Rails I18n routes with middleware

533 views Asked by At

I need to translate my site and I'm using I18n for this purpose. Using locale as URL param, I want to redirect users to their locale, which saved in their cookies.
Here is string from routes.rb which I'm using to redirect:

get "/path", to: redirect("/#{I18n.locale}/%{path}", status: 302), constraints: {path: /(?!(#{I18n.available_locales.join("|")})/)./}, format: false

And I'm using Rack middleware to get cookies and set I18n.locale before routes:

require 'i18n'

module Rack
  class Locale
    def initialize(app)
      @app = app
    end

    def call(env)
      request = ActionDispatch::Request.new(env)
      I18n.locale = request.cookies['locale'].to_sym if request.cookies['locale'].present? && request.params[:locale].nil?
      @app.call(env)
    end
  end
end

The problem is in routes.rb file: I18.locale is always set there to default locale, so there is no redirect to user's locale, but to the default locale.

Also, I've debugged middleware, and as I see, I18n.locale sets there successfully.

Any ideas how to set I18n.locale in routes.rb?

1

There are 1 answers

3
Jonas On

Is there a particular reason why you are using the locale as a part of your routes? If not I'd suggest you follow the Rails I18n guide which recommends to set the locale in a before_action hook which for your case then could fetch it from the cookie (code is quoted as is from the Rails guide):

before_action :set_locale

def set_locale
  I18n.locale = params[:locale] || I18n.default_locale
end