Rails以不同语言存储类别

时间:2011-06-23 08:26:04

标签: ruby-on-rails internationalization model

我正在构建一个多重应用程序,它有两个基本模型类别产品,其中类别有许多产品< /强> ..

所以我希望能够使用多种语言显示相同的类别,例如,考虑一个名为Cars的类别,对于使用法语版本的用户,它应该显示为 Vehicules 应用

我怎么能这样做?我应该把它们存放在不同的型号吗?或者我应该在类别模型中添加 lang 列?

我想要做的是在Category模型中添加 lang 列并添加 default_scope 调用以将其范围仅搜索所需的语言,我有两个但问题是:

  1. 如何从模型内部获取使用过的语言,即I18n调用?我应该采用哪种方法?
  2. 使用此技术会产生问题,引用法语类别的产品不会出现在英语类别下的搜索中,我该如何解决此问题?
  3. 谢谢

3 个答案:

答案 0 :(得分:2)

您必须问自己的一个关键问题是,汽车类别是否应与汽车类别相同的对象(暗示相同的对象和相同的URL)是否重要。

如果它们属于同一类别,那么唯一的问题是如何将名称翻译成不同的语言。如果您支持的语言数量相对较少,则可以使用不同的列(name_enname_fr等)将它们全部存储在模型中。

或者您可以单独存储翻译的名称,例如使用I18n模块。

或者,如果Cars和Vehicules是单独的类别,那么您可以按照建议向模型添加lang属性。

答案 1 :(得分:1)

Frankie Roberto 给了你一个很好的答案。我将添加一些额外的信息。

首先是简单部分:在模型中获取当前区域设置

如果您将控制器中的语言设置为I18n.locale = something,那么您可以以相同的方式在模型中阅读它。毕竟,I18n是一个全局常量。

现在关于搜索

我通常更喜欢您拥有一个类别的设计,但该类别的名称已翻译为多种语言。一辆车属于“汽车”类别而另一辆属于“汽车”类别的设计是有缺陷的恕我直言。在后一种情况下,没有任何意义可以使它成为单个站点 - 您可以创建一个单语言应用程序,并将其安装在多个实例中,其中每个实例都被翻译成单一语言。

如果您有一个简短的静态受支持语言列表,则可以为每种语言添加一列:name_enname_frname_pl

如果您的应用程序设计时语言列表很大或未知,那么将“名称”(作为示例给出)存储为序列化哈希会更容易。因此,您可以将目标翻译设为name["fr"]name["de"]等等。

我已经学会了(很难:-))用户通常懒得提供所有翻译(或者他们只是不知道所有语言),因此您应该准备好一些模型使用您试图显示或搜索的语言中的数据。

对于每个“已翻译”属性,您可能需要准备一种方法,以便在缺少所需的翻译时为您提供最合适的翻译。

此方法的工作方式类似于:

def translated_name
  ([I18n.locale] + other_languages).each do |l|
    return name[l] unless name[l].blank?
  end
  return "" # or some default value - possibly from I18n.t("some.static.default")
end

当然,您不需要使用I18n.locale,您应该以(理想情况下)匹配用户语言首选项的方式定义other_languages,可能通过分析“Accept-Language”标题。 / p>

我有时会使用方法名称name_for(lang)name_in(lang),如果我必须支持更多的数据语言而不是接口(我将翻译并放入I18n配置文件中)。

啊,是的 - 搜索。 :)

如果您已将“名称”定义为单独的属性,则可以只搜索相应的列。

如果您将“名称”作为单个序列化哈希,则可以将该列作为简单文本进行搜索(但我不确定YAML是否不会破坏非ASCII字符)或者使用可搜索的数据创建另一个列,然后(在模型级别,而不是在SQL级别)将模型划分为组:“已在您的语言中找到搜索字符串”,“搜索字符串已在其他语言中找到“。我相信多语服务的用户会对以这种方式呈现的搜索结果感到满意。

答案 2 :(得分:0)

我正在使用这个宝石来解决这类问题:https://github.com/jo/puret