aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRobin Houston <robin.houston@gmail.com>2012-03-20 15:06:18 +0000
committerRobin Houston <robin.houston@gmail.com>2012-03-20 15:06:18 +0000
commitac108a6c3ac503dc185a12d502653fca597eeacd (patch)
treea03b1a8372d89402349036a1c491bd87289bdc0a
parent6d55519425c41cd292a7dfe0809e0e59d9504b56 (diff)
Fix the "log in as" function
Previously the "log in as" function after 3b6e5a692b852a88f55b21a7210f60a6f7cfc24b would attempt to log the admin user out before issuing the redirect. Unfortunately this approach does not work on WhatDoTheyKnow, where the admin pages are served via a different domain (secure.mysociety.org) and so do not share session information with the rest of the site. This commit changes it to mark the PostRedirect with circumstance == "login_as", which signals the user controller to log out the previous user even if they are an admin. In other words, the user is logged out on the main site rather than the admin site, skirting this problem. Closes #450.
-rw-r--r--app/controllers/admin_user_controller.rb3
-rw-r--r--app/controllers/application_controller.rb4
-rw-r--r--app/controllers/user_controller.rb2
-rw-r--r--app/models/post_redirect.rb2
-rw-r--r--spec/controllers/admin_user_controller_spec.rb10
-rw-r--r--spec/integration/admin_spec.rb24
6 files changed, 31 insertions, 14 deletions
diff --git a/app/controllers/admin_user_controller.rb b/app/controllers/admin_user_controller.rb
index b2c084739..249030537 100644
--- a/app/controllers/admin_user_controller.rb
+++ b/app/controllers/admin_user_controller.rb
@@ -74,10 +74,9 @@ class AdminUserController < AdminController
def login_as
@admin_user = User.find(params[:id]) # check user does exist
- post_redirect = PostRedirect.new( :uri => main_url(user_url(@admin_user)), :user_id => @admin_user.id)
+ post_redirect = PostRedirect.new( :uri => main_url(user_url(@admin_user)), :user_id => @admin_user.id, :circumstance => "login_as" )
post_redirect.save!
url = main_url(confirm_url(:email_token => post_redirect.email_token, :only_path => true))
- session[:user_id] = nil # Log out current (usually admin) user, so we get logged in as the other user
redirect_to url
end
diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb
index 506b57b60..0508abe76 100644
--- a/app/controllers/application_controller.rb
+++ b/app/controllers/application_controller.rb
@@ -151,8 +151,8 @@ class ApplicationController < ActionController::Base
false
end
- # Called from test code, is a mimic of User.confirm, for use in following email
- # links when in controller tests (since we don't have full integration tests that
+ # Called from test code, is a mimic of UserController.confirm, for use in following email
+ # links when in controller tests (though we also have full integration tests that
# can work over multiple controllers)
def test_code_redirect_by_email_token(token, controller_example_group)
post_redirect = PostRedirect.find_by_email_token(token)
diff --git a/app/controllers/user_controller.rb b/app/controllers/user_controller.rb
index 403cb9684..08726183e 100644
--- a/app/controllers/user_controller.rb
+++ b/app/controllers/user_controller.rb
@@ -182,7 +182,7 @@ class UserController < ApplicationController
return
end
- if !User.stay_logged_in_on_redirect?(@user)
+ if !User.stay_logged_in_on_redirect?(@user) || post_redirect.circumstance == "login_as"
@user = post_redirect.user
@user.email_confirmed = true
@user.save!
diff --git a/app/models/post_redirect.rb b/app/models/post_redirect.rb
index 59cc86799..c9a6229a4 100644
--- a/app/models/post_redirect.rb
+++ b/app/models/post_redirect.rb
@@ -39,7 +39,7 @@ class PostRedirect < ActiveRecord::Base
self.post_params_yaml = params.to_yaml
end
def post_params
- if self.post_params_yaml.nil?
+ if self.post_params_yaml.nil?
return {}
end
YAML.load(self.post_params_yaml)
diff --git a/spec/controllers/admin_user_controller_spec.rb b/spec/controllers/admin_user_controller_spec.rb
index 60ac6969d..c2d645fd2 100644
--- a/spec/controllers/admin_user_controller_spec.rb
+++ b/spec/controllers/admin_user_controller_spec.rb
@@ -24,13 +24,7 @@ describe AdminUserController, "when administering users" do
post_redirect = PostRedirect.get_last_post_redirect
response.should redirect_to(:controller => 'user', :action => 'confirm', :email_token => post_redirect.email_token)
end
-
- it "logs in as another user when already logged in as an admin" do
- session[:user_id] = users(:admin_user).id
- get :login_as, :id => users(:bob_smith_user).id
- post_redirect = PostRedirect.get_last_post_redirect
- response.should redirect_to(:controller => 'user', :action => 'confirm', :email_token => post_redirect.email_token)
- session[:user_id].should be_nil
- end
+
+ # See also "allows an admin to log in as another user" in spec/integration/admin_spec.rb
end
diff --git a/spec/integration/admin_spec.rb b/spec/integration/admin_spec.rb
new file mode 100644
index 000000000..7fecd60d2
--- /dev/null
+++ b/spec/integration/admin_spec.rb
@@ -0,0 +1,24 @@
+require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
+
+require "base64"
+
+describe "When administering the site" do
+ it "allows an admin to log in as another user" do
+ # First log in as Joe Admin
+ admin_user = users(:admin_user)
+ admin_user.email_confirmed = true
+ admin_user.save!
+ post_via_redirect "/profile/sign_in", :user_signin => {:email => admin_user.email, :password => "jonespassword"}
+ response.should be_success
+
+ # Now fetch the "log in as" link to log in as Bob
+ basic_auth_login @request
+ admin_username = MySociety::Config.get('ADMIN_USERNAME')
+ admin_password = MySociety::Config.get('ADMIN_PASSWORD')
+ get_via_redirect "/admin/user/login_as/#{users(:bob_smith_user).id}", nil, {
+ "Authorization" => "Basic " + Base64.b64encode("#{admin_username}:#{admin_password}").strip
+ }
+ response.should be_success
+ session[:user_id].should == users(:bob_smith_user).id
+ end
+end