【问题标题】:How to fix: i18n always translate to default locale如何修复:i18n 始终转换为默认语言环境
【发布时间】:2019-11-12 10:01:13
【问题描述】:

我正在尝试使用 i18n 对 Rails 应用程序进行国际化。我用两种语言做了一些小测试:英语和法语。

我遇到的问题是 i18n 总是转换为默认语言环境。所以如果是英文,一切都是英文的,法文也一样。

这是我尝试过的:

config/initializers/locales.rb

# Permitted locales available for the application
I18n.available_locales = [:en, :fr]

app/controllers/application_controller.rb

class ApplicationController < ActionController::Base

    def default_url_options
        { locale: I18n.locale }
    end

end

config/application.rb

module LanguageApp
  class Application < Rails::Application
    ...
    config.i18n.load_path += Dir["#{Rails.root.to_s}/config/locales/**/*.{rb,yml}"]
    config.i18n.default_locale = :en
    # I change the default locale here to :fr or :en
  end
end

config/routes.rb

root to: "home#index"

get '/:locale/about' => 'about#index'
get '/:locale' => 'home#index'

我这样组织我的 yml 文件:

config/locales/views/about/en.yml

en:
  about: "This page is about us."

config/locales/views/about/fr.yml

fr:
  about: "Cette page est à propos de nous."

config/locales/views/home/en.yml

en:
  welcome: "Hello world"

config/locales/views/home/fr.yml

fr:
  welcome: "Bonjour le monde"

最后是我的观点:

app/views/about/index.html.erb

About us page. <%= t(:about) %>

app/views/home/index.html.erb

This is the homepage. <%= t(:welcome) %>

我认为问题可能来自我组织 yml 文件的方式,但我不明白为什么 i18n 只翻译为默认语言环境并“忽略”另一种语言。

编辑:

为了在运行 rails 服务器的浏览器中尝试此操作,我尝试访问以下 URL:

localhost:3000
localhost:3000/en
localhost:3000/fr

这 3 个 URL 给了我相同的内容,所以 :fr 语言环境实际上不起作用(它返回与 :en 相同的翻译)

同样

localhost:3000/en/about
localhost:3000/fr/about

我也在rails控制台中试过:

> I18n.t(:welcome, :en)
"Hello world"
> I18n.t(:welcome, :fr)
"Hello world"

【问题讨论】:

  • 当新的语言环境来自 params 时,我看不到您正在设置/更改 I18n.locale
  • 我忘了提到我是如何改变它的。我正在编辑我的问题。

标签: ruby-on-rails ruby rails-i18n


【解决方案1】:

首先设置请求的语言环境:

class ApplicationController < ActionController::Base
    around_action :switch_locale
 
    def switch_locale(&action)
        I18n.with_locale(params[:locale] || I18n.default_locale, &action)
    end

    def default_url_options
        { locale: I18n.locale }
    end
end

不要像许多旧答案/教程那样使用I18n.locale=

I18n.locale 可能会泄漏到相同的后续请求中 如果在每个控制器中没有一致地设置线程/进程。为了 在一个 POST 请求中执行 I18n.locale = :es 的示例将具有 对未设置的控制器的所有后续请求的影响 语言环境,但仅在该特定线程/进程中。是因为, 而不是 I18n.locale = 你可以使用 I18n.with_locale 而不是 有这个泄漏问题。

如果你想为特定视图创建翻译,你应该嵌套键而不是仅仅使用平面散列:

en:
  home:
    welcome: "Hello World"

fr:
  home:
    welcome: "Bonjour le monde"

然后在视图中使用隐式查找:

<h1><%= t('.welcome') %></h1>

这会将密钥解析为home.welcome

【讨论】:

  • 谢谢,现在可以使用了。我缺少的是 switch_locale 方法,之后一切都很好。谢谢!
猜你喜欢
  • 1970-01-01
  • 2014-03-09
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-07-07
  • 1970-01-01
  • 2017-03-10
相关资源
最近更新 更多