多语言站点:URL上的语言作为dir,文件在其他地方.如何重定向


Multilanguage site: language on URL as dir, file elsewhere. How to redirect

现在我的网站只有一种语言。

我有我的文件(假设):

www.mysite.com/files/index.php
www.mysite.com/files/header.php
www.mysite.com/files/page1.php
www.mysite.com/files/page2.php

现在我为这些文件添加了多语言支持。所有的单词/文本都存储在数据库中,一个php类完成了这些工作。

到目前为止,我已经(严重地)在header.php上写了这一行:

define('LNG', 'en');

和我有一个header.php文件放在每个语言目录:

www.mysite.com/en/header.php
www.mysite.com/de/header.php
...

,然后我根据LNG常数包括文件,例如

include_once "/files/page1.php?l=".LNG

但我知道这是一个非常糟糕的做法!

我该如何解决这个问题?我会在www.mysite.com/files/...上维护我的文件,然后在URL中写入用户语言,以便文件可以从URL中读取语言并从数据库中加载正确的文本和单词。

:

www.mysite.com/en/index.php

实际上是加载

www.mysite.com/index.php

用正确的语言en。我能够从URL中获得en,并在页面上定义一个常量,但如果我指向www.mysite.com/en/index.php,我显然得到一个404

处理多语言web应用程序

LANGUAGE CONSTANTS 可以放在语言目录下的语言文件中,如

/ languages
  en.php
  it.php
  ...

而语言文件可能如下所示

// en.php
define("THANK_YOU", "Thank you!");
define("PRODUCTS", "Products");
define("PRODUCT", "Product");
...
// it.php
define("THANK_YOU", "Grazie!");
define("PRODUCTS", "Prodotti");
define("PRODUCT", "Prodotto");
....

也可以存储到数据库中,如下所示。两种方法我都用过,但我更喜欢第一种方法

+------------+------------+------------+-----
| constant   | en         | it         | ...
+------------+------------+------------+-----
| THANK_YOU  | Thank you! | Grazie!    |
| PRODUCTS   | Products   | Prodotti   |
| PRODUCT    | Product    | Prodotto   |
| ...        | ...        | ...        |
+------------+------------+------------+-----

FRIENDLY URLs 可能如下所示

http://www.domain.com
http://www.domain.com/en
http://www.domain.com/it
http://www.domain.com/en/products
http://www.domain.com/it/prodotti
http://www.domain.com/en/product/our-best-product/555
http://www.domain.com/it/prodotto/il-nostro-miglior-prodotto/555

考虑到.htaccess文件

中定义的规则
RewriteRule ^([a-z]+)(/)?$                                    index.php?lang=$1 [QSA,L]
RewriteRule ^([a-z]+)/(products|prodotti)(/)?$                index.php?lang=$1&action=$2 [NC,L]
RewriteRule ^([a-z]+)/(product|prodotto)/(.*)/([0-9]+)(/)?$   index.php?lang=$1&action=$2&id=$4&mode=details [NC,L]
# these rules are for a demonstration purpose; otherwise, all three directives 
# could be written in one singe line / rule   

或者您可以将请求(如下所示)重定向到一个入口点,并使用parse_url()对其进行解析。

RewriteCond  %{REQUEST_FILENAME} !-f
RewriteCond  %{REQUEST_FILENAME} !-d
RewriteRule  ^(.*)$ index.php?param=$1 [QSA,L] 

ACCESSING THE lang VARIABLE -在多语言项目中,变量lang具有特殊的意义,否则它将像其他变量一样被处理和传递,使用GET, POST, COOKIE, XMLHttpRequest, HTTP headers, HTTP referer, URL hash parameter, database session, APC (Alternative PHP Cache)

如果你关心UXSEO, lang变量应该写在URL中。我更喜欢使用$_SESSION或$_GET,应该指出的是,上面提到的一些方法并不总是工作或可能被代理阻止。

下面的代码片段显示了如何使用$_SESSION或$_GET

访问它
// config.php
// ...
$cfgObj->default_language = "en";
// ...
$_SESSION["lang"] = isset($_GET["lang"]) ? $_GET["lang"] : $cfgObj->default_lang;
include($cfgObj->dir_languages . $_SESSION["lang"] . ".php");
// index.php
switch(isset($_GET["action"]) ? $_GET["action"] : "default"){
    case PRODUCTS: case PRODUCT: case 3:
         // deal with products
         break:
    case ARTICLES: case ARTICLE: case 5:
         // deal with articles
         break:
    default: 
         // deal with short-links 
         // domain.com/3/555 <-- this would retrieve product with id 555 
         break;
}

DATABASE SCHEMA 可以这样设计

+-----------------+       +-----------------------+       +--------------------+
| products        |       | products_to_languages |       | languages          |
+-----------------+       +-----------------------+       +--------------------+
| product_id [PK] |---|   | ptl_id           [PK] |   |---| language_id   [PK] |
| price           |   |---| product_id       [FK] |   |   | language_code      |
| status          |       | languge_id       [FK] |---|   +--------------------+
| ...             |       | product_name          |  
+-----------------+       | product_description   |
                          +-----------------------+
* I use language_code as a primary key as well, and an index on all foreign keys