diff --git a/CHANGELOG.rdoc b/CHANGELOG.rdoc index c2fb0ab9..8f2c4b47 100644 --- a/CHANGELOG.rdoc +++ b/CHANGELOG.rdoc @@ -9,6 +9,7 @@ Notes: https://github.com/plataformatec/devise/wiki/How-To:-Upgrade-to-Devise-2. * Do not run validations unless on reconfirmable branch * enhancements + * Redirect to the previous URL on timeout * Inherit from the same Devise parent controller (by @sj26) * Allow parent_controller to be customizable via Devise.parent_controller, useful for engines * Allow router_name to be customizable via Devise.router_name, useful for engines diff --git a/lib/devise/failure_app.rb b/lib/devise/failure_app.rb index 6fb1314b..18e08205 100644 --- a/lib/devise/failure_app.rb +++ b/lib/devise/failure_app.rb @@ -53,14 +53,19 @@ module Devise def redirect store_location! - flash[:alert] = i18n_message + if flash[:timedout] && flash[:alert] + flash.keep(:timedout) + flash.keep(:alert) + else + flash[:alert] = i18n_message + end redirect_to redirect_url end protected def i18n_message(default = nil) - message = warden.message || warden_options[:message] || default || :unauthenticated + message = warden_message || default || :unauthenticated if message.is_a?(Symbol) I18n.t(:"#{scope}.#{message}", :resource_name => scope, @@ -71,6 +76,15 @@ module Devise end def redirect_url + if warden_message == :timeout + flash[:timedout] = true + attempted_path || scope_path + else + scope_path + end + end + + def scope_path opts = {} route = :"new_#{scope}_session_path" opts[:format] = request_format unless skip_format? @@ -139,6 +153,10 @@ module Devise env['warden.options'] end + def warden_message + @message ||= warden.message || warden_options[:message] + end + def scope @scope ||= warden_options[:scope] || Devise.default_scope end diff --git a/test/integration/timeoutable_test.rb b/test/integration/timeoutable_test.rb index 48e3de09..44cee0de 100644 --- a/test/integration/timeoutable_test.rb +++ b/test/integration/timeoutable_test.rb @@ -41,7 +41,7 @@ class SessionTimeoutTest < ActionController::IntegrationTest assert_not_nil last_request_at get users_path - assert_redirected_to new_user_session_path + assert_redirected_to users_path assert_not warden.authenticated?(:user) end @@ -68,7 +68,7 @@ class SessionTimeoutTest < ActionController::IntegrationTest get expire_user_path(user) get users_path - assert_redirected_to new_user_session_path + assert_redirected_to users_path assert_not warden.authenticated?(:user) end end @@ -80,17 +80,31 @@ class SessionTimeoutTest < ActionController::IntegrationTest user = sign_in_as_user get expire_user_path(user) - get users_path + get root_path follow_redirect! assert_contain 'Session expired!' end end - + + test 'error message with i18n with double redirect' do + store_translations :en, :devise => { + :failure => { :user => { :timeout => 'Session expired!' } } + } do + user = sign_in_as_user + + get expire_user_path(user) + get users_path + follow_redirect! + follow_redirect! + assert_contain 'Session expired!' + end + end + test 'time out not triggered if remembered' do user = sign_in_as_user :remember_me => true get expire_user_path(user) assert_not_nil last_request_at - + get users_path assert_response :success assert warden.authenticated?(:user)