实现多语言URL的最佳方法是什么?

5
我正在开发一个利基社交网站,该网站即将支持多语言。这意味着我们当前的URL结构很快需要开始使用翻译后的单词来表示像以下这样的斜杠:

www.example.com/home 变成 www.example.com/inicio

www.example.com/profile 变成 www.example.com/perfil

www.example.com/help 变成 www.example.com/ayuda

等等。我的问题是:在PHP应用程序中支持这种结构的最佳方法是什么?对于传入的请求,我认为在我的router.php文件中使用以下类似字典的方式就足够了:

<?php
$request = explode("/", trim($_SERVER['REQUEST_URI'], "/"));

// Dictionaries of page slugs.
$slugs = array(
    'es' => array(
        'inicio' => 'home',
        'perfil' => 'profile',
        'ayuda' => 'help',
    )
    // additional languages can be added here
);

// Rewrite any incoming (foreign) requests
if ($host=="www.example.es") { // to be made programmatic
    $lang = "es"; // pick up from locale constant rather being hard-coded
    if (array_key_exists($request[0], $slugs[$lang])) {
        $request[0] = $slugs[$lang][$request[0]];
    }
}

...

这基本上是将URL段与其英文对应项进行匹配。如果没有找到,则会正常执行,并且很可能会因为URL段的控制器不存在而导致404错误。

虽然如此,我也希望它具备向后兼容性。例如,在我的应用程序中构建URL时。

目前应用程序只支持英语,因此这些内容都是硬编码的。所以说,当获取一个User对象时,我会执行以下操作:

<?php
class User {

    function __construct($id) {
        // fetch user details
        $this->profile_url = ROOT . "/profile/" . $this->username;
    }
}

什么是最佳方法来替换硬编码的"/profile/",以获取翻译版本,例如在西班牙网站中使用"/perfil/"

你是在使用某种PHP框架,还是自己编写的系统? - mth
在翻译时,我通常选择将页面实际存储在数据库中,通过ID或内部名称引用它们,并使它们成为具有方法(例如getUrl())的完整对象,这些方法可能是区域设置感知的。 - Wrikken
翻译后的路径片段非常罕见。我的直觉是要避免使其过于灵活。 - mario
这是我所在组织内部的自定义框架,随着我们走向国际化,翻译路径片段是一个必要的要求。 - Martin Bean
4个回答

2

我可能会错,但是还是试一下...

实现多语言网站的标准方法是使用 i18n 字典/模板技术,其中每种语言都有一个单独的字典,在某些情况下还有不同的模板。

然而,在这种情况下,我从来没有见过有人改变他们的 URL 语言。URL 将请求映射到服务器磁盘上的文件(一般来说),因此如果可以避免,就不应该根据语言更改 URL。

常见的做法是在 URL 的“路径”部分前缀中加入您要请求的语言 - 即: http://foo.bar/en-us/foobar.html

总结: 我不会担心翻译您的 URL,因为这不是一种标准做法(至少我没有看到过)。只需在 URL 的“路径”前缀中加入语言表示,例如上面的 URL。


会不会是一种语言“播音员”呢? :P - Richard Marskell - Drackir
确实如此,尽管我认为“指示”是更好的同义词。我已经在上面进行了更正。 - Craige

1

我正在开发的应用程序中有类似的东西。

每个页面都有一个唯一的ID,与表格中每种语言的slug、页面标题、元描述等匹配。

至于那些说这不是标准做法,不必费心的人,我不同意,因为在不同的语言中拥有漂亮的翻译URL可以帮助您的SEO。


完全是我的想法。感谢您的意见。 - Martin Bean

1

嗯,我看到的PHP常见模式是为每种语言创建一个PHP文件,并初始化一个大型字典,其中所有语言的键都相同。

有一个名为language的会话变量,最初可以是英语(或您喜欢的任何语言)的“en”,然后使用命令“include(language.'/main.php');”进行包含,其中您有一个名为“en”的文件夹,其中包含所有要包含的翻译的PHP文件。如果主文件过大,您可以将其细分并包含适合您需求的任何翻译(例如/en/forum.php用于论坛翻译和/en/blob.php用于首页翻译)。

它具有极大的灵活性,使您能够通过修改一个会话变量来控制语言。您甚至可以像检测浏览器语言设置一样做一些技巧,并根据尚未定义的语言进行分配,而不仅仅是将其设为英语。


是的。我希望使用本地变量或常量与 gettext 结合使用,以确定要调用哪种语言内容和 URL。 - Martin Bean
我认为关键在于您不必担心URL。语言切换/加载的内容由服务器处理。 - Richard Marskell - Drackir

0

我正在思考这个问题,因为我现在正在走这条路。我原本打算使用类似的方法,但不完全相同...

我原本打算使用语言“包含”文件来存储网站中的所有字符串。所以...

/languages/en.php

英文语言将拥有所有正确的字符串,其他语言文件可以作为新翻译而添加。

在en.php文件中,我打算放入这样的字段

define('PageTitleWelcomeMessage', 'Welcome to Foo');

然后在网站的任何地方调用该静态变量。英文语言将在他们的个人资料中定义

我可以这样调用该变量:

echo PageTitleWelcomeMessage;

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接