Issue #1301460 by loganfsmyth, good_man, Gábor Hojtsy, xjm: Decouple domain/path language negotiation storage from language config storage.
parent
7135589c89
commit
c42985ffb3
|
@ -2690,21 +2690,18 @@ function language_list($field = 'language') {
|
|||
* A language object.
|
||||
*/
|
||||
function language_default() {
|
||||
return variable_get(
|
||||
$default = variable_get(
|
||||
'language_default',
|
||||
(object) array(
|
||||
'language' => 'en',
|
||||
'name' => 'English',
|
||||
'direction' => 0,
|
||||
'enabled' => 1,
|
||||
'plurals' => 0,
|
||||
'formula' => '',
|
||||
'domain' => '',
|
||||
'prefix' => '',
|
||||
'weight' => 0,
|
||||
'javascript' => ''
|
||||
)
|
||||
);
|
||||
$default->default = TRUE;
|
||||
return $default;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -424,8 +424,9 @@ function language_url_split_prefix($path, $languages) {
|
|||
$prefix = array_shift($args);
|
||||
|
||||
// Search prefix within enabled languages.
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
foreach ($languages as $language) {
|
||||
if (!empty($language->prefix) && $language->prefix == $prefix) {
|
||||
if (isset($prefixes[$language->language]) && $prefixes[$language->language] == $prefix) {
|
||||
// Rebuild $path with the language removed.
|
||||
return array($language, implode('/', $args));
|
||||
}
|
||||
|
|
|
@ -279,12 +279,13 @@ function locale_language_from_url($languages) {
|
|||
break;
|
||||
|
||||
case LOCALE_LANGUAGE_NEGOTIATION_URL_DOMAIN:
|
||||
$domains = locale_language_negotiation_url_domains();
|
||||
foreach ($languages as $language) {
|
||||
// Skip check if the language doesn't have a domain.
|
||||
if ($language->domain) {
|
||||
if (!empty($domains[$language->language])) {
|
||||
// Only compare the domains not the protocols or ports.
|
||||
// Remove protocol and add http:// so parse_url works
|
||||
$host = 'http://' . str_replace(array('http://', 'https://'), '', $language->domain);
|
||||
$host = 'http://' . str_replace(array('http://', 'https://'), '', $domains[$language->language]);
|
||||
$host = parse_url($host, PHP_URL_HOST);
|
||||
if ($_SERVER['HTTP_HOST'] == $host) {
|
||||
$language_url = $language->language;
|
||||
|
@ -337,7 +338,9 @@ function locale_language_url_fallback($language = NULL, $language_type = LANGUAG
|
|||
// If the default language is not configured to convey language information,
|
||||
// a missing URL language information indicates that URL language should be
|
||||
// the default one, otherwise we fall back to an already detected language.
|
||||
if (($prefix && empty($default->prefix)) || (!$prefix && empty($default->domain))) {
|
||||
$domains = locale_language_negotiation_url_domains();
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
if (($prefix && empty($prefixes[$default->language])) || (!$prefix && empty($domains[$default->language]))) {
|
||||
return $default->language;
|
||||
}
|
||||
else {
|
||||
|
@ -428,22 +431,52 @@ function locale_language_url_rewrite_url(&$path, &$options) {
|
|||
if (isset($options['language'])) {
|
||||
switch (variable_get('locale_language_negotiation_url_part', LOCALE_LANGUAGE_NEGOTIATION_URL_PREFIX)) {
|
||||
case LOCALE_LANGUAGE_NEGOTIATION_URL_DOMAIN:
|
||||
if ($options['language']->domain) {
|
||||
$domains = locale_language_negotiation_url_domains();
|
||||
if (!empty($domains[$options['language']->language])) {
|
||||
// Ask for an absolute URL with our modified base_url.
|
||||
$options['absolute'] = TRUE;
|
||||
$options['base_url'] = $options['language']->domain;
|
||||
$options['base_url'] = $domains[$options['language']->language];
|
||||
}
|
||||
break;
|
||||
|
||||
case LOCALE_LANGUAGE_NEGOTIATION_URL_PREFIX:
|
||||
if (!empty($options['language']->prefix)) {
|
||||
$options['prefix'] = $options['language']->prefix . '/';
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
if (!empty($prefixes[$options['language']->language])) {
|
||||
$options['prefix'] = $prefixes[$options['language']->language] . '/';
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads language prefixes and uses the langcode if no prefix is set.
|
||||
*/
|
||||
function locale_language_negotiation_url_prefixes() {
|
||||
return variable_get('locale_language_negotiation_url_prefixes', array());
|
||||
}
|
||||
|
||||
/**
|
||||
* Saves language prefix settings.
|
||||
*/
|
||||
function locale_language_negotiation_url_prefixes_save(array $prefixes) {
|
||||
variable_set('locale_language_negotiation_url_prefixes', $prefixes);
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads language domains.
|
||||
*/
|
||||
function locale_language_negotiation_url_domains() {
|
||||
return variable_get('locale_language_negotiation_url_domains', array());
|
||||
}
|
||||
|
||||
/**
|
||||
* Saves the language domain settings.
|
||||
*/
|
||||
function locale_language_negotiation_url_domains_save(array $domains) {
|
||||
variable_set('locale_language_negotiation_url_domains', $domains);
|
||||
}
|
||||
|
||||
/**
|
||||
* Rewrite URLs for the Session language provider.
|
||||
*/
|
||||
|
@ -509,10 +542,6 @@ function locale_string_is_safe($string) {
|
|||
*/
|
||||
function locale_language_save($language) {
|
||||
$language->is_new = !(bool) db_query_range('SELECT 1 FROM {languages} WHERE language = :language', 0, 1, array(':language' => $language->language))->fetchField();
|
||||
// Default prefix on language code if not provided otherwise.
|
||||
if (!isset($language->prefix)) {
|
||||
$language->prefix = $language->language;
|
||||
}
|
||||
|
||||
// If name was not set, we add a predefined language.
|
||||
if (!isset($language->name)) {
|
||||
|
|
|
@ -173,15 +173,6 @@ function locale_language_overview_form_submit($form, &$form_state) {
|
|||
}
|
||||
$language->enabled = (int) !empty($form_state['values']['languages'][$langcode]['enabled']);
|
||||
|
||||
// If language URL prefixes are enabled we must clear language domains and
|
||||
// assign a valid prefix to each non-default language.
|
||||
if ($url_prefixes) {
|
||||
$language->domain = '';
|
||||
if (empty($language->prefix) && !$language->default) {
|
||||
$language->prefix = $langcode;
|
||||
}
|
||||
}
|
||||
|
||||
locale_language_save($language);
|
||||
}
|
||||
|
||||
|
@ -704,20 +695,21 @@ function locale_language_providers_url_form($form, &$form_state) {
|
|||
);
|
||||
|
||||
$languages = language_list('enabled');
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
$domains = locale_language_negotiation_url_domains();
|
||||
foreach ($languages[1] as $langcode => $language) {
|
||||
$form['prefix'][$langcode] = array(
|
||||
'#type' => 'textfield',
|
||||
'#title' => t('%language (%langcode) path prefix', array('%language' => $language->name, '%langcode' => $language->language)),
|
||||
'#maxlength' => 64,
|
||||
'#default_value' => $language->prefix,
|
||||
'#field_prefix' => url(NULL, array('absolute' => TRUE)) . (variable_get('clean_url', 0) ? '' : '?q=')
|
||||
|
||||
'#default_value' => isset($prefixes[$langcode]) ? $prefixes[$langcode] : '',
|
||||
'#field_prefix' => url('', array('absolute' => TRUE)) . (variable_get('clean_url', 0) ? '' : '?q=')
|
||||
);
|
||||
$form['domain'][$langcode] = array(
|
||||
'#type' => 'textfield',
|
||||
'#title' => t('%language (%langcode) domain', array('%language' => $language->name, '%langcode' => $language->language)),
|
||||
'#maxlength' => 128,
|
||||
'#default_value' => $language->domain,
|
||||
'#default_value' => isset($domains[$langcode]) ? $domains[$langcode] : '',
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -784,21 +776,9 @@ function locale_language_providers_url_form_submit($form, &$form_state) {
|
|||
// Save selected format (prefix or domain).
|
||||
variable_set('locale_language_negotiation_url_part', $form_state['values']['locale_language_negotiation_url_part']);
|
||||
|
||||
$languages = language_list('enabled');
|
||||
$default = language_default();
|
||||
|
||||
foreach ($languages[1] as $langcode => $language) {
|
||||
|
||||
// Add new prefix and domain settings to the language object.
|
||||
foreach (array('prefix', 'domain') as $type) {
|
||||
if (isset($form_state['values'][$type][$langcode])) {
|
||||
$language->$type = $form_state['values'][$type][$langcode];
|
||||
}
|
||||
}
|
||||
|
||||
// Save the prefix and domain settings for each language.
|
||||
locale_language_save($language);
|
||||
}
|
||||
// Save new domain and prefix values.
|
||||
locale_language_negotiation_url_prefixes_save($form_state['values']['prefix']);
|
||||
locale_language_negotiation_url_domains_save($form_state['values']['domain']);
|
||||
|
||||
drupal_set_message(t('Configuration saved.'));
|
||||
}
|
||||
|
|
|
@ -39,6 +39,8 @@ function locale_uninstall() {
|
|||
variable_del('language_count');
|
||||
variable_del('language_types');
|
||||
variable_del('locale_language_negotiation_url_part');
|
||||
variable_del('locale_language_negotiation_url_prefixes');
|
||||
variable_del('locale_language_negotiation_url_domains');
|
||||
variable_del('locale_language_negotiation_session_param');
|
||||
variable_del('language_content_type_default');
|
||||
variable_del('language_content_type_negotiation');
|
||||
|
@ -99,20 +101,6 @@ function locale_schema() {
|
|||
'default' => 0,
|
||||
'description' => 'Enabled flag (1 = Enabled, 0 = Disabled).',
|
||||
),
|
||||
'domain' => array(
|
||||
'type' => 'varchar',
|
||||
'length' => 128,
|
||||
'not null' => TRUE,
|
||||
'default' => '',
|
||||
'description' => 'Domain to use for this language.',
|
||||
),
|
||||
'prefix' => array(
|
||||
'type' => 'varchar',
|
||||
'length' => 128,
|
||||
'not null' => TRUE,
|
||||
'default' => '',
|
||||
'description' => 'Path prefix to use for this language.',
|
||||
),
|
||||
'weight' => array(
|
||||
'type' => 'int',
|
||||
'not null' => TRUE,
|
||||
|
@ -277,6 +265,37 @@ function locale_update_8002() {
|
|||
db_drop_field('locales_source', 'textgroup');
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes the prefix and domain columns from the language table.
|
||||
*
|
||||
* Load all prefixes and domains from the languages table, save the values in
|
||||
* two new variables. Then remove the prefix and domain columns from the
|
||||
* languages table.
|
||||
*/
|
||||
function locale_update_8003() {
|
||||
|
||||
// Look up languages directly instead of using language_list().
|
||||
$languages = db_select('languages', 'l')
|
||||
->fields('l')
|
||||
->execute();
|
||||
|
||||
// Collect all domains and prefixes.
|
||||
$prefixes = array();
|
||||
$domains = array();
|
||||
foreach ($languages as $language) {
|
||||
$prefixes[$language->language] = $language->prefix;
|
||||
$domains[$language->language] = $language->domain;
|
||||
}
|
||||
|
||||
// Save the prefix and domain values in a variable.
|
||||
variable_set('locale_language_negotiation_url_prefixes', $prefixes);
|
||||
variable_set('locale_language_negotiation_url_domains', $domains);
|
||||
|
||||
// Remove the prefix and domain columns.
|
||||
db_drop_field('languages', 'prefix');
|
||||
db_drop_field('languages', 'domain');
|
||||
}
|
||||
|
||||
/**
|
||||
* @} End of "addtogroup updates-7.x-to-8.x"
|
||||
* The next series of updates should start at 9000.
|
||||
|
|
|
@ -607,6 +607,56 @@ function locale_modules_disabled($modules) {
|
|||
locale_modules_enabled($modules);
|
||||
}
|
||||
|
||||
/**
|
||||
* Implements hook_locale_language_insert().
|
||||
*/
|
||||
function locale_locale_language_insert($language) {
|
||||
// Add new language to the list of language prefixes.
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
$prefixes[$language->language] = (empty($language->default) ? $language->language : '');
|
||||
locale_language_negotiation_url_prefixes_save($prefixes);
|
||||
|
||||
// Add language to the list of language domains.
|
||||
$domains = locale_language_negotiation_url_domains();
|
||||
$domains[$language->language] = '';
|
||||
locale_language_negotiation_url_domains_save($domains);
|
||||
}
|
||||
|
||||
/**
|
||||
* Implements hook_locale_language_update().
|
||||
*/
|
||||
function locale_locale_language_update($language) {
|
||||
|
||||
// If the language is the default, then ensure that no other languages have
|
||||
// blank prefix codes.
|
||||
if (!empty($language->default)) {
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
foreach ($prefixes as $langcode => $prefix) {
|
||||
if ($prefix == '' && $langcode != $language->language) {
|
||||
$prefixes[$langcode] = $langcode;
|
||||
}
|
||||
}
|
||||
locale_language_negotiation_url_prefixes_save($prefixes);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Implements hook_locale_language_delete().
|
||||
*/
|
||||
function locale_locale_language_delete($language) {
|
||||
// Remove language from language prefix list.
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
unset($prefixes[$language->language]);
|
||||
locale_language_negotiation_url_prefixes_save($prefixes);
|
||||
|
||||
// Remove language from language domain list.
|
||||
$domains = locale_language_negotiation_url_domains();
|
||||
unset($domains[$language->language]);
|
||||
locale_language_negotiation_url_domains_save($domains);
|
||||
}
|
||||
|
||||
|
||||
// ---------------------------------------------------------------------------------
|
||||
// Locale core functionality
|
||||
|
||||
|
|
|
@ -2346,7 +2346,6 @@ class LocaleUrlRewritingTest extends DrupalWebTestCase {
|
|||
// Check URL rewriting with a non-installed language.
|
||||
$non_existing = language_default();
|
||||
$non_existing->language = $this->randomName();
|
||||
$non_existing->prefix = $this->randomName();
|
||||
$this->checkUrl($non_existing, t('Path language is ignored if language is not installed.'), t('URL language negotiation does not work with non-installed languages'));
|
||||
}
|
||||
|
||||
|
@ -2364,11 +2363,15 @@ class LocaleUrlRewritingTest extends DrupalWebTestCase {
|
|||
$segments = explode('/', $rewritten_path, 2);
|
||||
$prefix = $segments[0];
|
||||
$path = isset($segments[1]) ? $segments[1] : $prefix;
|
||||
// If the rewritten URL has not a language prefix we pick the right one from
|
||||
// the language object so we can always check the prefixed URL.
|
||||
if ($this->assertNotEqual($language->prefix, $prefix, $message1)) {
|
||||
$prefix = $language->prefix;
|
||||
|
||||
// If the rewritten URL has not a language prefix we pick a random prefix so
|
||||
// we can always check the prefixed URL.
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
$stored_prefix = isset($prefixes[$language->language]) ? $prefixes[$language->language] : $this->randomName();
|
||||
if ($this->assertNotEqual($stored_prefix, $prefix, $message1)) {
|
||||
$prefix = $stored_prefix;
|
||||
}
|
||||
|
||||
$this->drupalGet("$prefix/$path");
|
||||
$this->assertResponse(404, $message2);
|
||||
}
|
||||
|
@ -2568,9 +2571,10 @@ class LocaleCommentLanguageFunctionalTest extends DrupalWebTestCase {
|
|||
$this->drupalPost("node/add/article", $edit, t('Save'));
|
||||
$node = $this->drupalGetNodeByTitle($title);
|
||||
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
foreach (language_list() as $langcode => $language) {
|
||||
// Post a comment with content language $langcode.
|
||||
$prefix = empty($language->prefix) ? '' : $language->prefix . '/';
|
||||
$prefix = empty($prefixes[$langcode]) ? '' : $prefixes[$langcode] . '/';
|
||||
$edit = array("comment_body[$langcode_none][0][value]" => $this->randomName());
|
||||
$this->drupalPost("{$prefix}node/{$node->nid}", $edit, t('Save'));
|
||||
|
||||
|
|
|
@ -1288,7 +1288,13 @@ class DrupalWebTestCase extends DrupalTestCase {
|
|||
// Set to English to prevent exceptions from utf8_truncate() from t()
|
||||
// during install if the current language is not 'en'.
|
||||
// The following array/object conversion is copied from language_default().
|
||||
$language = (object) array('language' => 'en', 'name' => 'English', 'native' => 'English', 'direction' => 0, 'enabled' => 1, 'plurals' => 0, 'formula' => '', 'domain' => '', 'prefix' => '', 'weight' => 0, 'javascript' => '');
|
||||
$language = (object) array(
|
||||
'language' => 'en',
|
||||
'name' => 'English',
|
||||
'direction' => 0,
|
||||
'enabled' => 1,
|
||||
'weight' => 0,
|
||||
);
|
||||
|
||||
// Save and clean shutdown callbacks array because it static cached and
|
||||
// will be changed by the test run. If we don't, then it will contain
|
||||
|
|
|
@ -77,8 +77,9 @@ class TranslationTestCase extends DrupalWebTestCase {
|
|||
|
||||
// Check that the "add translation" link uses a localized path.
|
||||
$languages = language_list();
|
||||
$prefixes = locale_language_negotiation_url_prefixes();
|
||||
$this->drupalGet('node/' . $node->nid . '/translate');
|
||||
$this->assertLinkByHref($languages['es']->prefix . '/node/add/' . str_replace('_', '-', $node->type), 0, t('The "add translation" link for %language points to the localized path of the target language.', array('%language' => $languages['es']->name)));
|
||||
$this->assertLinkByHref($prefixes['es'] . '/node/add/' . str_replace('_', '-', $node->type), 0, t('The "add translation" link for %language points to the localized path of the target language.', array('%language' => $languages['es']->name)));
|
||||
|
||||
// Submit translation in Spanish.
|
||||
$node_translation_title = $this->randomName();
|
||||
|
@ -88,8 +89,8 @@ class TranslationTestCase extends DrupalWebTestCase {
|
|||
// Check that the "edit translation" and "view node" links use localized
|
||||
// paths.
|
||||
$this->drupalGet('node/' . $node->nid . '/translate');
|
||||
$this->assertLinkByHref($languages['es']->prefix . '/node/' . $node_translation->nid . '/edit', 0, t('The "edit" link for the translation in %language points to the localized path of the translation language.', array('%language' => $languages['es']->name)));
|
||||
$this->assertLinkByHref($languages['es']->prefix . '/node/' . $node_translation->nid, 0, t('The "view" link for the translation in %language points to the localized path of the translation language.', array('%language' => $languages['es']->name)));
|
||||
$this->assertLinkByHref($prefixes['es'] . '/node/' . $node_translation->nid . '/edit', 0, t('The "edit" link for the translation in %language points to the localized path of the translation language.', array('%language' => $languages['es']->name)));
|
||||
$this->assertLinkByHref($prefixes['es'] . '/node/' . $node_translation->nid, 0, t('The "view" link for the translation in %language points to the localized path of the translation language.', array('%language' => $languages['es']->name)));
|
||||
|
||||
// Attempt to submit a duplicate translation by visiting the node/add page
|
||||
// with identical query string.
|
||||
|
|
Loading…
Reference in New Issue