From aa0e68d653f85d06af9d5d04b0bc24f8fc1c61d0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E9=B3=A5=E4=BA=95=20=E9=9B=AA?= Date: Wed, 14 Jan 2015 13:20:33 +0900 Subject: [PATCH] Refactor #set_locale in applicaiton_controller by dividing the method to 3 methods each decides locales from given conditions. --- app/controllers/application_controller.rb | 46 ++++++---- .../application_controller_spec.rb | 86 +++++++++++++++++++ 2 files changed, 114 insertions(+), 18 deletions(-) create mode 100644 spec/controllers/application_controller_spec.rb diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index d46e69f..04c336b 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -75,28 +75,38 @@ class ApplicationController < ActionController::Base end def set_locale - available = I18n.available_locales.map(&:to_s) - if params[:lang] && available.include?(params[:lang]) + # NOTE: ignoring q=xxx in request header for now + I18n.locale = locale_from_params || locale_from_session || locale_from_http_accept_lang || I18n.default_locale + end + + def locale_from_params + if params[:lang] && available_locales.include?(params[:lang]) session[:prefer_lang] = params[:lang] - I18n.locale = params[:lang] - return + params[:lang] + else + nil end - if session[:prefer_lang] - I18n.locale = session[:prefer_lang] - return + end + + def locale_from_session + session[:prefer_lang] + end + + def locale_from_http_accept_lang + return nil if request.env["HTTP_ACCEPT_LANGUAGE"].blank? + + langs = request.env["HTTP_ACCEPT_LANGUAGE"].gsub(/q=[0-9.]+/, "").gsub(";","").split(",") + prefer = langs.find { |lang| available_locales.include?(lang) } + + unless prefer + prefer = :en if langs.find{ |lang| lang.match(/^en/) } end - # NOTE: ignoring q=xxx in request header for now - return if request.env["HTTP_ACCEPT_LANGUAGE"].blank? - langs = request.env["HTTP_ACCEPT_LANGUAGE"].gsub(/q=[0-9.]+/, "").gsub(";","").split(",") - prefer = langs.find {|lang| available.include?(lang) } - unless prefer - if langs.find{|lang| lang.match(/^en/)} - I18n.locale = :en - return - end - end - I18n.locale = prefer + prefer + end + + def available_locales + @available_locales ||= I18n.available_locales.map(&:to_s) end def file_tail(path, limit = 10) diff --git a/spec/controllers/application_controller_spec.rb b/spec/controllers/application_controller_spec.rb new file mode 100644 index 0000000..e469064 --- /dev/null +++ b/spec/controllers/application_controller_spec.rb @@ -0,0 +1,86 @@ +require 'spec_helper' + +class DummyController < ApplicationController; end + +describe DummyController do + controller DummyController do + skip_before_action :login_required + def index + render :text => "Hello World" + end + end + + describe '#set_locale' do + let!(:default_locale) { :en } + before do + I18n.stub(:default_locale).and_return(default_locale) + I18n.stub(:available_locales).and_return([:en, :ja]) + + I18n.locale = I18n.default_locale #initialize + end + + context 'with params[:lang]' do + before do + get 'index', lang: param_lang + end + + context 'and in available_locales' do + let(:param_lang) { :ja } + + it 'params[:lang] will be set as locale' do + expect(I18n.locale).to eq :ja + end + end + + context 'and out of available_locales' do + let(:param_lang) { :ka } + + it 'defalut locale will be set as locale' do + expect(I18n.locale).to eq default_locale + end + end + end + + context 'with session[:prefer_lang]' do + before do + controller.session[:prefer_lang] = :ja + end + + it 'session[:prefer_lang] will be set as locale' do + get 'index' + expect(I18n.locale).to eq :ja + end + end + + context 'with request.env["HTTP_ACCEPT_LANGUAGE"]' do + before do + request.stub(:env).and_return({ "HTTP_ACCEPT_LANGUAGE" => accept_language }) + get 'index' + end + + context 'accept_language is available' do + let(:accept_language) { 'ja' } + + it 'session[:prefer_lang] will be set as locale' do + expect(I18n.locale).to eq :ja + end + end + + context 'accept_language is not available but start with en' do + let(:accept_language) { 'en-us' } + + it ':en will be set as locale' do + expect(I18n.locale).to eq :en + end + end + + context 'accept_language is not available' do + let(:accept_language) { 'ka' } + + it 'default_locale will be set as locale' do + expect(I18n.locale).to eq default_locale + end + end + end + end +end