? 615258-path-source.patch Index: API.php =================================================================== RCS file: /cvs/drupal-contrib/contributions/modules/domain/API.php,v retrieving revision 1.49 diff -u -p -r1.49 API.php --- API.php 24 Oct 2009 22:11:26 -0000 1.49 +++ API.php 1 Nov 2009 16:29:57 -0000 @@ -334,6 +334,46 @@ function hook_domainwarnings() { } /** + * Allows modules to specify the target link for a node. + * + * @param &$source + * The domain array from domain_get_node_match(), passed by reference. + * @param $nid + * The node id. + * @return + * No return value; modify $source by reference. + */ +function hook_domain_source_alter(&$source, $nid) { + // Taken from the Domain Source module + $source = domain_source_lookup($nid); +} + +/** + * Allows modules to specify the target link for a Drupal path. + * + * Note: This hook is not meant to be used for node paths, which + * are handled by hook_domain_source_alter(). This hook is split + * from hook_domain_source_alter() for better performance. + * + * Currently, no modules in the package implement this hook. + * + * @param &$source + * The domain array from domain_get_node_match(), passed by reference. + * @param $nid + * The identifier of the obect being rewritten. For nodes, this is the node id. + * In other instances, we may pass a $path string or other variable. + * @return + * No return value; modify $source by reference. + */ +function hook_domain_source_path_alter(&$source, $path) { + // Always make admin links go to the primary domain. + $base = arg(0, $path); + if ($base == 'admin') { + $source = domain_default(); + } +} + +/** * Allows modules to add additional form elements for saving as domain-specific * settings. * Index: domain.module =================================================================== RCS file: /cvs/drupal-contrib/contributions/modules/domain/domain.module,v retrieving revision 1.132 diff -u -p -r1.132 domain.module --- domain.module 31 Oct 2009 18:28:32 -0000 1.132 +++ domain.module 1 Nov 2009 16:30:00 -0000 @@ -309,10 +309,8 @@ function domain_block($op = 'list', $del if (!empty($this_node->subdomains)) { $output .= theme('item_list', $this_node->subdomains, t('Assigned domains')); } - if (isset($this_node->domain_source)) { - $this_domain = domain_lookup($this_node->domain_source); - $output .= theme('item_list', array($this_domain['sitename']), t('Source domain')); - } + $this_domain = domain_get_node_match($this_node->nid); + $output .= theme('item_list', array($this_domain['sitename']), t('Source domain')); if (empty($output)) { $output = t('This node is not assigned to a domain.'); } @@ -1153,6 +1151,45 @@ function domain_nodeapi(&$node, $op, $a3 } /** + * Get the best matching domain for a node link. + * + * @param $nid + * The node id. + * @return + * The domain array for the best matching domain for links to this node. + */ +function domain_get_node_match($nid) { + static $domain = array(); + if (isset($domain[$nid])) { + return $domain[$nid]; + } + // Load the domain data for this node -- but only take the first match. + $id = db_result(db_query_range("SELECT gid FROM {domain_access} WHERE nid = %d AND realm = '%s' ORDER BY gid", $nid, 'domain_id', 0, 1)); + $source = domain_lookup($id); + drupal_alter('domain_source', $source, $nid); + $domain[$nid] = $source; + return $source; +} + +/** + * Allow the lookup of path rewrites. + * + * Note that unlinke domain_get_node_match(), this function assumes + * that all links will be written to the current domain. + * + * @param $path + * The link path. + * @return + * The domain array for the best matching domain for links to this node. + */ +function domain_get_path_match($path) { + global $_domain; + $source = $_domain; + drupal_alter('domain_source_path', $source, $path); + return $source; +} + +/** * Get the domains for a node. * * @param $nid @@ -1846,24 +1883,24 @@ function domain_invalid_domain_requested } // Try to find the proper redirect for a node. $path = "node/$node->nid"; - if (isset($node->domain_source)) { - $domain = domain_lookup($node->domain_source); - if ($domain['valid']) { - $redirect = $domain; - } - else if (!empty($node->domains)) { - foreach ($node->domains as $domain_id) { - if ($domain_id == -1) { - $domain_id = 0; - } - $domain = domain_lookup($domain_id); - if ($domain['valid']) { - $redirect = $domain; - break; - } + + $domain = domain_get_node_match($node->nid); + if ($domain['valid']) { + $redirect = $domain; + } + else if (!empty($node->domains)) { + foreach ($node->domains as $domain_id) { + if ($domain_id == -1) { + $domain_id = 0; + } + $domain = domain_lookup($domain_id); + if ($domain['valid']) { + $redirect = $domain; + break; } } } + // If we found no node matches, just go to the home page. $extra = ' '. t('node page.'); if (empty($redirect)) { Index: settings_custom_url.inc =================================================================== RCS file: /cvs/drupal-contrib/contributions/modules/domain/settings_custom_url.inc,v retrieving revision 1.24 diff -u -p -r1.24 settings_custom_url.inc --- settings_custom_url.inc 24 Oct 2009 16:18:52 -0000 1.24 +++ settings_custom_url.inc 1 Nov 2009 16:30:01 -0000 @@ -40,43 +40,63 @@ function domain_url_outbound_alter(&$pat } // Set static variables for the node lookups, to remove redundant queries. - static $domain_site, $domain, $nodepaths, $path_rewrite; + static $domain_site, $domain, $nodepaths, $path_rewrite, $use_source, $root, $check_nodes, $path_lookup, $path_alter; // This routine only needs to be run from certain urls or if we want to // force all links to go to a single domain for SEO. // See http://drupal.org/node/195366 for the background. + + // These two functions are statically cached elsewhere. + // Are we viewing nodes from all sites? $check = domain_grant_all(); + // Are we forcing path rewrites? $seo = variable_get('domain_seo', 0); - // If using Domain Source, we force links to a specific domain. - $use_source = function_exists('domain_source_lookup'); - - if ($check || $seo || $use_source) { - // Check to see if this is a node or comment link and set $nid accordingly. - // We static the $nid results to make this more efficient. - $pattern = explode('/', $original_path); + // Check for source rewrites. + if (!isset($use_source)) { + $use_source = (bool) count(module_implements('domain_source_alter')); + } + // Querying for nodepaths is expensive, so only do it if needed. + if (!isset($check_nodes)) { + $check_nodes = $check || $seo || $use_source; + } + // Check for path rewrites. + if (!isset($path_alter)) { + $path_alter = (bool) count(module_implements('domain_source_path_alter')); + } + // Get the root url. + if (!isset($root)) { + $root = domain_lookup(variable_get('domain_default_source', 0)); + } - // Advanced pattern matching, we find the node id based on token %n in the path string. - if (!isset($nodepaths)) { - $pathdata = variable_get('domain_paths', "node/%n\r\nnode/%n/edit\r\ncomment/reply/%n\r\nnode/add/book/parent/%n\r\nbook/export/html/%n\r\nnode/%n/outline"); - $path_match = preg_replace('/(\r\n?|\n)/', '|', $pathdata); - $nodepaths = explode("|", $path_match); - } + // Now run the path rewrite sequence, if necessary. + if ($check_nodes || $path_alter) { $nid = FALSE; - foreach ($nodepaths as $match) { - $match_array = explode('/', $match); - $placeholder = array_search('%n', $match_array); - if (isset($pattern[$placeholder])) { - $match_array[$placeholder] = $pattern[$placeholder]; - if (is_numeric($pattern[$placeholder]) && $match_array == $pattern) { - $nid = (int) $pattern[$placeholder]; - break; + $target_domain_id = $_domain['domain_id']; + if ($check_nodes) { + // Check to see if this is a node or comment link and set $nid accordingly. + // We static the $nid results to make this more efficient. + $pattern = explode('/', $original_path); + + // Advanced pattern matching, we find the node id based on token %n in the path string. + if (!isset($nodepaths)) { + $pathdata = variable_get('domain_paths', "node/%n\r\nnode/%n/edit\r\ncomment/reply/%n\r\nnode/add/book/parent/%n\r\nbook/export/html/%n\r\nnode/%n/outline"); + $path_match = preg_replace('/(\r\n?|\n)/', '|', $pathdata); + $nodepaths = explode("|", $path_match); + } + foreach ($nodepaths as $match) { + $match_array = explode('/', $match); + $placeholder = array_search('%n', $match_array); + if (isset($pattern[$placeholder])) { + $match_array[$placeholder] = $pattern[$placeholder]; + if (is_numeric($pattern[$placeholder]) && $match_array == $pattern) { + $nid = (int) $pattern[$placeholder]; + break; + } } } } - $target_domain_id = $_domain['domain_id']; // This path has matched a node id, so it may need to be rewritten. - if ($nid) { - $root = domain_lookup(variable_get('domain_default_source', 0)); + if (!empty($nid)) { // Remove redundancy from the domain_site check. if (!isset($domain_site[$nid])) { // If this check works, we don't need to rewrite the path unless SEO rules demand it. @@ -85,16 +105,7 @@ function domain_url_outbound_alter(&$pat if (!$domain_site[$nid] || $use_source) { // Remove rendundancy from the domain_id check. if (!isset($domain[$nid])) { - // The Domain Source module is optional, and allows nodes to be assigned to specific domains for the - // purpose of this check. - if ($use_source) { - $domain[$nid] = domain_source_lookup($nid); - } - else { - // Load the domain data for this node -- but only take the first match. - $id = db_result(db_query_range("SELECT gid FROM {domain_access} WHERE nid = %d AND realm = '%s' ORDER BY gid", $nid, 'domain_id', 0, 1)); - $domain[$nid] = domain_lookup($id); - } + $domain[$nid] = domain_get_node_match($nid); } // Can we and do we need to rewrite this path? if ($domain[$nid] != -1 && $domain[$nid]['domain_id'] != $_domain['domain_id']) { @@ -117,6 +128,21 @@ function domain_url_outbound_alter(&$pat $target_domain_id = $root['domain_id']; } } + // Hook for non-node paths. + else if (!empty($path_alter)) { + // Must use md5 here, to prevent array keys from breaking. + $name = md5($path); + if (!isset($path_lookup[$name])) { + $path_lookup[$name] = domain_get_path_match($path); + } + if ($path_lookup[$name] != $_domain) { + $options['absolute'] = TRUE; + // In this case, the $base_url cannot have a trailing slash + $options['base_url'] = rtrim($path_lookup[$name]['path'], '/'); + $target_domain_id = $path_lookup[$name]['domain_id']; + // TODO: merge this code with the above for cleanup. + } + } // We may have to implement hook_domainpath(). if (!isset($path_rewrite)) { $path_rewrite = count(_domain_path_modules()); Index: domain_source/domain_source.module =================================================================== RCS file: /cvs/drupal-contrib/contributions/modules/domain/domain_source/domain_source.module,v retrieving revision 1.17 diff -u -p -r1.17 domain_source.module --- domain_source/domain_source.module 24 Oct 2009 21:02:51 -0000 1.17 +++ domain_source/domain_source.module 1 Nov 2009 16:30:01 -0000 @@ -180,7 +180,7 @@ function domain_source_nodeapi(&$node, $ break; case 'load': if ($node->nid) { - $source = domain_source_lookup($node, $node->domains, $node->domain_site); + $source = domain_source_lookup($node->nid, $node->domains, $node->domain_site); $node->domain_source = $source['domain_id']; } break; @@ -190,7 +190,7 @@ function domain_source_nodeapi(&$node, $ // calls that are neither a teaser nor a page view. if ($a3 !== FALSE || $a4 !== FALSE) { if (variable_get('domain_debug', 0) && user_access('set domain access') && isset($node->domain_source)) { - $source = domain_lookup($node->domain_source); + $source = domain_get_node_match($node->nid); $extra = ' '; $use_active = db_result(db_query("SELECT domain_id FROM {domain_source} WHERE nid = %d", $node->nid)); if (empty($use_active)) { @@ -218,7 +218,9 @@ function domain_source_nodeapi(&$node, $ */ function domain_source_lookup($nid, $domains = array(), $domain_site = FALSE) { global $_domain; + $source = db_result(db_query("SELECT domain_id FROM {domain_source} WHERE nid = %d", $nid)); + if (empty($source)) { $source = variable_get('domain_default_source', 0); } @@ -244,6 +246,20 @@ function domain_source_lookup($nid, $dom } /** + * Implement hook_domain_source_node_alter(). + * + * @param &$source + * The domain array from domain_get_node_match(), passed by reference. + * @param $nid + * The node id. + * @return + * No return value; modify $source by reference. + */ +function domain_source_domain_source_alter(&$source, $nid) { + $source = domain_source_lookup($nid); +} + +/** * FormAPI function that lets us update access rules. */ function domain_source_update_nodes($form, &$form_state) {