15

I have a multilingual site with Drupal 7 using subdomains like en.example.com to detect the language. Everything works like expected, but I have a mobile version of the website witch I want to be accessible by domains like en.m.example.com etc. How do I do this? I can set in admin/config/regional/language only one domain per language, but would have to set two in order to get that working, like:

for English:
en.example.com & en.m.example.com

for German:
de.example.com & de.m.example.com
etc.

(I would like to have the same structure as Wikipedia has.) The problem is, that using subdomains for language selection, Drupal creates all internal links as absolute pathes. For example, a menu link will be created as:

<li class="menu-773"><a href="http://en.example.com/test" >test</a></li>
and not as
<li class="menu-773"><a href="/test" >test</a></li>

So, I could create a domain alias with Apache, to send requests from en.m.example.com to en.example.com, but all internal links would bring the user back from the mobile version to the normal. How can I solve this problem?

  • 1
    This doesn't really answer your question exactly but it would be better not to have separate mobile sites. It would be better to have a responsive layout that changes for mobile. It gives a better experience, it is easier to maintain, and you skip the negatives of browser detection and switching sites. - It will require a bit of investment in design/themeing though. – rooby Apr 20 '13 at 14:29
  • Thank you, I know that this is generally the best. But the use case of my website is different for mobile and normal users. So the functions and the content, that will be delivered differs as well. That why I do not have that option. – user5950 Apr 20 '13 at 15:23
  • I don't understand this! This is a basic thing. It must be possible to use Drupal with languages domain in combination with subdomins for a mobile theme. Isn't there anybody out there doing this with Drupal? – user5950 Apr 20 '13 at 15:57
5

Once you've set up Drupal to serve different languages in different domains, you need to instruct your web server to send requests from multiple domains to the same Drupal site.

In Apache, you'll need to edit the .conf (httpd.conf) file and add aliases to all the different domains. For example:

ServerName en.example.com
ServerAlias en.m.example.com

In addition to this, you'll also need to point the domain name server (DNS) to your server for all the domain names in different languages.

  • That does not work for me. The problem is that using different domains for language selection as described above, results in all internal links being created as absolute paths. So I can reach the page with en.example.com & en.m.example.com, but all internal link under en.m.example.com does not have the second sub domin, for example a link to a sub page looks like en.example.com/node/1234 , but should look like en.m.example.com/node/1234. – user5950 Mar 27 '13 at 12:20
2

The answer is: using multiple domains for one language is not possible with Drupal 7 and there is – as far as I know – no module that adds that functionality.

But to achieve this aim anyway, there is workaround: As mentioned above, the problem with language domains is, that all internal pathes that have an language specific path alias and are created with the Drupal core function url() are created as absolute pathes. Responsible for that behaviour is the function:

locale_language_url_rewrite_url(&$path, &$options)
  1. Don't set a language domain for that default language. If you don't do that, Drupal will not create absolute pathes for the default language if – for example – use the domain xyz.example.com, where xyz.example.com is not set as domain for any language, Drupal will create al urls relative and so clicking of any internal link will keep the subdomain. But you can't use that method, if you want to have language sensitive subdomains as described above:

    for English: en.example.com & en.m.example.com

    for German: de.example.com & de.m.example.com etc.

  2. So the second method would be, to alter the current language of all types with the function: hook_language_init. I use the following code, to get the above example working:

:

# hook_language_init()
function my_module_language_init() {
  // Current path
  $url = $_SERVER['SERVER_NAME'];

  // Global language object and get languages
  global $language;
  $languages = language_list();

  // Get all subdomains
  $reg = '/^((?:([^\.]+)\.)?(?:([^\.]+)\.))?([^\.]+\.[^\.]+)$/i';
  preg_match($reg, $url, $up);

  # We won't allow all subdomains, only 'm.' and 'm2.'
  # Change this for an other use case.
  if ($up[3] == "m2" || $up[3] == "m") {

    if (!isset($languages[$up[2]])) {
      $langcode = $language->language;
    } else { 
      $langcode = $up[2];
    }
    $new_language         = $languages[$langcode];
    $new_language->domain = $new_language->language . "." . $up[3] .".". $up[4];

    // Set url options
    $options['language'] = $new_language;
    $types = language_types();

    // Set all language types and language domains
    foreach ($types as $type) {
      $GLOBALS[$type] = $new_language;
      $GLOBALS[$type]->domain = $new_language->domain;
    }
  }
}
  • I believe this module does something similar: drupal.org/project/language_multidomain BUT... I wonder why it's not possible to use this hook: api.drupal.org/api/drupal/modules!system!language.api.php/… (which is what the locale module uses) to define language negotiation provider that handles multiple domains?? – leon.nk Aug 15 '13 at 10:54
  • @leon.nk I did not find that module, thank you for that hint. Maybe you are right and the hook_language_negotiation_info is the right hook to use. I'll try it. – user5950 Aug 15 '13 at 13:17
  • Apparently the language_multidomain module does not exist any more. – Matthias Urlichs Oct 3 '13 at 11:14
  • Shouldn't the above hook be hook_language_init()? There is no hook_api_language_init(). You should also update the language switcher links with hook_language_switch_links_alter(). – colan Feb 10 '14 at 17:39
  • @colan The custom module is called custom_api and the hook hook_language_init(). Together it is custom_api_language_init(). May be this is confusing, so I edited the example to make that point clear. You are right, to use ´hook_language_switch_links_alter()´ may be the better way. But as it seems that almost nobody is interested in this problem, I think it may not be worth to rewrite this example. – user5950 Feb 10 '14 at 18:21

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.