##// END OF EJS Templates
Activate sudo mode after password based login (#20589)....
Jean-Philippe Lang -
r14253:16cc9ec06a57
parent child
Show More
@@ -1,354 +1,355
1 # Redmine - project management software
1 # Redmine - project management software
2 # Copyright (C) 2006-2015 Jean-Philippe Lang
2 # Copyright (C) 2006-2015 Jean-Philippe Lang
3 #
3 #
4 # This program is free software; you can redistribute it and/or
4 # This program is free software; you can redistribute it and/or
5 # modify it under the terms of the GNU General Public License
5 # modify it under the terms of the GNU General Public License
6 # as published by the Free Software Foundation; either version 2
6 # as published by the Free Software Foundation; either version 2
7 # of the License, or (at your option) any later version.
7 # of the License, or (at your option) any later version.
8 #
8 #
9 # This program is distributed in the hope that it will be useful,
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 # GNU General Public License for more details.
12 # GNU General Public License for more details.
13 #
13 #
14 # You should have received a copy of the GNU General Public License
14 # You should have received a copy of the GNU General Public License
15 # along with this program; if not, write to the Free Software
15 # along with this program; if not, write to the Free Software
16 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
16 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17
17
18 class AccountController < ApplicationController
18 class AccountController < ApplicationController
19 helper :custom_fields
19 helper :custom_fields
20 include CustomFieldsHelper
20 include CustomFieldsHelper
21
21
22 # prevents login action to be filtered by check_if_login_required application scope filter
22 # prevents login action to be filtered by check_if_login_required application scope filter
23 skip_before_filter :check_if_login_required, :check_password_change
23 skip_before_filter :check_if_login_required, :check_password_change
24
24
25 # Overrides ApplicationController#verify_authenticity_token to disable
25 # Overrides ApplicationController#verify_authenticity_token to disable
26 # token verification on openid callbacks
26 # token verification on openid callbacks
27 def verify_authenticity_token
27 def verify_authenticity_token
28 unless using_open_id?
28 unless using_open_id?
29 super
29 super
30 end
30 end
31 end
31 end
32
32
33 # Login request and validation
33 # Login request and validation
34 def login
34 def login
35 if request.get?
35 if request.get?
36 if User.current.logged?
36 if User.current.logged?
37 redirect_back_or_default home_url, :referer => true
37 redirect_back_or_default home_url, :referer => true
38 end
38 end
39 else
39 else
40 authenticate_user
40 authenticate_user
41 end
41 end
42 rescue AuthSourceException => e
42 rescue AuthSourceException => e
43 logger.error "An error occured when authenticating #{params[:username]}: #{e.message}"
43 logger.error "An error occured when authenticating #{params[:username]}: #{e.message}"
44 render_error :message => e.message
44 render_error :message => e.message
45 end
45 end
46
46
47 # Log out current user and redirect to welcome page
47 # Log out current user and redirect to welcome page
48 def logout
48 def logout
49 if User.current.anonymous?
49 if User.current.anonymous?
50 redirect_to home_url
50 redirect_to home_url
51 elsif request.post?
51 elsif request.post?
52 logout_user
52 logout_user
53 redirect_to home_url
53 redirect_to home_url
54 end
54 end
55 # display the logout form
55 # display the logout form
56 end
56 end
57
57
58 # Lets user choose a new password
58 # Lets user choose a new password
59 def lost_password
59 def lost_password
60 (redirect_to(home_url); return) unless Setting.lost_password?
60 (redirect_to(home_url); return) unless Setting.lost_password?
61 if params[:token]
61 if params[:token]
62 @token = Token.find_token("recovery", params[:token].to_s)
62 @token = Token.find_token("recovery", params[:token].to_s)
63 if @token.nil? || @token.expired?
63 if @token.nil? || @token.expired?
64 redirect_to home_url
64 redirect_to home_url
65 return
65 return
66 end
66 end
67 @user = @token.user
67 @user = @token.user
68 unless @user && @user.active?
68 unless @user && @user.active?
69 redirect_to home_url
69 redirect_to home_url
70 return
70 return
71 end
71 end
72 if request.post?
72 if request.post?
73 @user.password, @user.password_confirmation = params[:new_password], params[:new_password_confirmation]
73 @user.password, @user.password_confirmation = params[:new_password], params[:new_password_confirmation]
74 if @user.save
74 if @user.save
75 @token.destroy
75 @token.destroy
76 flash[:notice] = l(:notice_account_password_updated)
76 flash[:notice] = l(:notice_account_password_updated)
77 redirect_to signin_path
77 redirect_to signin_path
78 return
78 return
79 end
79 end
80 end
80 end
81 render :template => "account/password_recovery"
81 render :template => "account/password_recovery"
82 return
82 return
83 else
83 else
84 if request.post?
84 if request.post?
85 email = params[:mail].to_s
85 email = params[:mail].to_s
86 user = User.find_by_mail(email)
86 user = User.find_by_mail(email)
87 # user not found
87 # user not found
88 unless user
88 unless user
89 flash.now[:error] = l(:notice_account_unknown_email)
89 flash.now[:error] = l(:notice_account_unknown_email)
90 return
90 return
91 end
91 end
92 unless user.active?
92 unless user.active?
93 handle_inactive_user(user, lost_password_path)
93 handle_inactive_user(user, lost_password_path)
94 return
94 return
95 end
95 end
96 # user cannot change its password
96 # user cannot change its password
97 unless user.change_password_allowed?
97 unless user.change_password_allowed?
98 flash.now[:error] = l(:notice_can_t_change_password)
98 flash.now[:error] = l(:notice_can_t_change_password)
99 return
99 return
100 end
100 end
101 # create a new token for password recovery
101 # create a new token for password recovery
102 token = Token.new(:user => user, :action => "recovery")
102 token = Token.new(:user => user, :action => "recovery")
103 if token.save
103 if token.save
104 # Don't use the param to send the email
104 # Don't use the param to send the email
105 recipent = user.mails.detect {|e| email.casecmp(e) == 0} || user.mail
105 recipent = user.mails.detect {|e| email.casecmp(e) == 0} || user.mail
106 Mailer.lost_password(token, recipent).deliver
106 Mailer.lost_password(token, recipent).deliver
107 flash[:notice] = l(:notice_account_lost_email_sent)
107 flash[:notice] = l(:notice_account_lost_email_sent)
108 redirect_to signin_path
108 redirect_to signin_path
109 return
109 return
110 end
110 end
111 end
111 end
112 end
112 end
113 end
113 end
114
114
115 # User self-registration
115 # User self-registration
116 def register
116 def register
117 (redirect_to(home_url); return) unless Setting.self_registration? || session[:auth_source_registration]
117 (redirect_to(home_url); return) unless Setting.self_registration? || session[:auth_source_registration]
118 if request.get?
118 if request.get?
119 session[:auth_source_registration] = nil
119 session[:auth_source_registration] = nil
120 @user = User.new(:language => current_language.to_s)
120 @user = User.new(:language => current_language.to_s)
121 else
121 else
122 user_params = params[:user] || {}
122 user_params = params[:user] || {}
123 @user = User.new
123 @user = User.new
124 @user.safe_attributes = user_params
124 @user.safe_attributes = user_params
125 @user.admin = false
125 @user.admin = false
126 @user.register
126 @user.register
127 if session[:auth_source_registration]
127 if session[:auth_source_registration]
128 @user.activate
128 @user.activate
129 @user.login = session[:auth_source_registration][:login]
129 @user.login = session[:auth_source_registration][:login]
130 @user.auth_source_id = session[:auth_source_registration][:auth_source_id]
130 @user.auth_source_id = session[:auth_source_registration][:auth_source_id]
131 if @user.save
131 if @user.save
132 session[:auth_source_registration] = nil
132 session[:auth_source_registration] = nil
133 self.logged_user = @user
133 self.logged_user = @user
134 flash[:notice] = l(:notice_account_activated)
134 flash[:notice] = l(:notice_account_activated)
135 redirect_to my_account_path
135 redirect_to my_account_path
136 end
136 end
137 else
137 else
138 @user.login = params[:user][:login]
138 @user.login = params[:user][:login]
139 unless user_params[:identity_url].present? && user_params[:password].blank? && user_params[:password_confirmation].blank?
139 unless user_params[:identity_url].present? && user_params[:password].blank? && user_params[:password_confirmation].blank?
140 @user.password, @user.password_confirmation = user_params[:password], user_params[:password_confirmation]
140 @user.password, @user.password_confirmation = user_params[:password], user_params[:password_confirmation]
141 end
141 end
142
142
143 case Setting.self_registration
143 case Setting.self_registration
144 when '1'
144 when '1'
145 register_by_email_activation(@user)
145 register_by_email_activation(@user)
146 when '3'
146 when '3'
147 register_automatically(@user)
147 register_automatically(@user)
148 else
148 else
149 register_manually_by_administrator(@user)
149 register_manually_by_administrator(@user)
150 end
150 end
151 end
151 end
152 end
152 end
153 end
153 end
154
154
155 # Token based account activation
155 # Token based account activation
156 def activate
156 def activate
157 (redirect_to(home_url); return) unless Setting.self_registration? && params[:token].present?
157 (redirect_to(home_url); return) unless Setting.self_registration? && params[:token].present?
158 token = Token.find_token('register', params[:token].to_s)
158 token = Token.find_token('register', params[:token].to_s)
159 (redirect_to(home_url); return) unless token and !token.expired?
159 (redirect_to(home_url); return) unless token and !token.expired?
160 user = token.user
160 user = token.user
161 (redirect_to(home_url); return) unless user.registered?
161 (redirect_to(home_url); return) unless user.registered?
162 user.activate
162 user.activate
163 if user.save
163 if user.save
164 token.destroy
164 token.destroy
165 flash[:notice] = l(:notice_account_activated)
165 flash[:notice] = l(:notice_account_activated)
166 end
166 end
167 redirect_to signin_path
167 redirect_to signin_path
168 end
168 end
169
169
170 # Sends a new account activation email
170 # Sends a new account activation email
171 def activation_email
171 def activation_email
172 if session[:registered_user_id] && Setting.self_registration == '1'
172 if session[:registered_user_id] && Setting.self_registration == '1'
173 user_id = session.delete(:registered_user_id).to_i
173 user_id = session.delete(:registered_user_id).to_i
174 user = User.find_by_id(user_id)
174 user = User.find_by_id(user_id)
175 if user && user.registered?
175 if user && user.registered?
176 register_by_email_activation(user)
176 register_by_email_activation(user)
177 return
177 return
178 end
178 end
179 end
179 end
180 redirect_to(home_url)
180 redirect_to(home_url)
181 end
181 end
182
182
183 private
183 private
184
184
185 def authenticate_user
185 def authenticate_user
186 if Setting.openid? && using_open_id?
186 if Setting.openid? && using_open_id?
187 open_id_authenticate(params[:openid_url])
187 open_id_authenticate(params[:openid_url])
188 else
188 else
189 password_authentication
189 password_authentication
190 end
190 end
191 end
191 end
192
192
193 def password_authentication
193 def password_authentication
194 user = User.try_to_login(params[:username], params[:password], false)
194 user = User.try_to_login(params[:username], params[:password], false)
195
195
196 if user.nil?
196 if user.nil?
197 invalid_credentials
197 invalid_credentials
198 elsif user.new_record?
198 elsif user.new_record?
199 onthefly_creation_failed(user, {:login => user.login, :auth_source_id => user.auth_source_id })
199 onthefly_creation_failed(user, {:login => user.login, :auth_source_id => user.auth_source_id })
200 else
200 else
201 # Valid user
201 # Valid user
202 if user.active?
202 if user.active?
203 successful_authentication(user)
203 successful_authentication(user)
204 update_sudo_timestamp! # activate Sudo Mode
204 else
205 else
205 handle_inactive_user(user)
206 handle_inactive_user(user)
206 end
207 end
207 end
208 end
208 end
209 end
209
210
210 def open_id_authenticate(openid_url)
211 def open_id_authenticate(openid_url)
211 back_url = signin_url(:autologin => params[:autologin])
212 back_url = signin_url(:autologin => params[:autologin])
212 authenticate_with_open_id(
213 authenticate_with_open_id(
213 openid_url, :required => [:nickname, :fullname, :email],
214 openid_url, :required => [:nickname, :fullname, :email],
214 :return_to => back_url, :method => :post
215 :return_to => back_url, :method => :post
215 ) do |result, identity_url, registration|
216 ) do |result, identity_url, registration|
216 if result.successful?
217 if result.successful?
217 user = User.find_or_initialize_by_identity_url(identity_url)
218 user = User.find_or_initialize_by_identity_url(identity_url)
218 if user.new_record?
219 if user.new_record?
219 # Self-registration off
220 # Self-registration off
220 (redirect_to(home_url); return) unless Setting.self_registration?
221 (redirect_to(home_url); return) unless Setting.self_registration?
221 # Create on the fly
222 # Create on the fly
222 user.login = registration['nickname'] unless registration['nickname'].nil?
223 user.login = registration['nickname'] unless registration['nickname'].nil?
223 user.mail = registration['email'] unless registration['email'].nil?
224 user.mail = registration['email'] unless registration['email'].nil?
224 user.firstname, user.lastname = registration['fullname'].split(' ') unless registration['fullname'].nil?
225 user.firstname, user.lastname = registration['fullname'].split(' ') unless registration['fullname'].nil?
225 user.random_password
226 user.random_password
226 user.register
227 user.register
227 case Setting.self_registration
228 case Setting.self_registration
228 when '1'
229 when '1'
229 register_by_email_activation(user) do
230 register_by_email_activation(user) do
230 onthefly_creation_failed(user)
231 onthefly_creation_failed(user)
231 end
232 end
232 when '3'
233 when '3'
233 register_automatically(user) do
234 register_automatically(user) do
234 onthefly_creation_failed(user)
235 onthefly_creation_failed(user)
235 end
236 end
236 else
237 else
237 register_manually_by_administrator(user) do
238 register_manually_by_administrator(user) do
238 onthefly_creation_failed(user)
239 onthefly_creation_failed(user)
239 end
240 end
240 end
241 end
241 else
242 else
242 # Existing record
243 # Existing record
243 if user.active?
244 if user.active?
244 successful_authentication(user)
245 successful_authentication(user)
245 else
246 else
246 handle_inactive_user(user)
247 handle_inactive_user(user)
247 end
248 end
248 end
249 end
249 end
250 end
250 end
251 end
251 end
252 end
252
253
253 def successful_authentication(user)
254 def successful_authentication(user)
254 logger.info "Successful authentication for '#{user.login}' from #{request.remote_ip} at #{Time.now.utc}"
255 logger.info "Successful authentication for '#{user.login}' from #{request.remote_ip} at #{Time.now.utc}"
255 # Valid user
256 # Valid user
256 self.logged_user = user
257 self.logged_user = user
257 # generate a key and set cookie if autologin
258 # generate a key and set cookie if autologin
258 if params[:autologin] && Setting.autologin?
259 if params[:autologin] && Setting.autologin?
259 set_autologin_cookie(user)
260 set_autologin_cookie(user)
260 end
261 end
261 call_hook(:controller_account_success_authentication_after, {:user => user })
262 call_hook(:controller_account_success_authentication_after, {:user => user })
262 redirect_back_or_default my_page_path
263 redirect_back_or_default my_page_path
263 end
264 end
264
265
265 def set_autologin_cookie(user)
266 def set_autologin_cookie(user)
266 token = Token.create(:user => user, :action => 'autologin')
267 token = Token.create(:user => user, :action => 'autologin')
267 cookie_options = {
268 cookie_options = {
268 :value => token.value,
269 :value => token.value,
269 :expires => 1.year.from_now,
270 :expires => 1.year.from_now,
270 :path => (Redmine::Configuration['autologin_cookie_path'] || '/'),
271 :path => (Redmine::Configuration['autologin_cookie_path'] || '/'),
271 :secure => (Redmine::Configuration['autologin_cookie_secure'] ? true : false),
272 :secure => (Redmine::Configuration['autologin_cookie_secure'] ? true : false),
272 :httponly => true
273 :httponly => true
273 }
274 }
274 cookies[autologin_cookie_name] = cookie_options
275 cookies[autologin_cookie_name] = cookie_options
275 end
276 end
276
277
277 # Onthefly creation failed, display the registration form to fill/fix attributes
278 # Onthefly creation failed, display the registration form to fill/fix attributes
278 def onthefly_creation_failed(user, auth_source_options = { })
279 def onthefly_creation_failed(user, auth_source_options = { })
279 @user = user
280 @user = user
280 session[:auth_source_registration] = auth_source_options unless auth_source_options.empty?
281 session[:auth_source_registration] = auth_source_options unless auth_source_options.empty?
281 render :action => 'register'
282 render :action => 'register'
282 end
283 end
283
284
284 def invalid_credentials
285 def invalid_credentials
285 logger.warn "Failed login for '#{params[:username]}' from #{request.remote_ip} at #{Time.now.utc}"
286 logger.warn "Failed login for '#{params[:username]}' from #{request.remote_ip} at #{Time.now.utc}"
286 flash.now[:error] = l(:notice_account_invalid_creditentials)
287 flash.now[:error] = l(:notice_account_invalid_creditentials)
287 end
288 end
288
289
289 # Register a user for email activation.
290 # Register a user for email activation.
290 #
291 #
291 # Pass a block for behavior when a user fails to save
292 # Pass a block for behavior when a user fails to save
292 def register_by_email_activation(user, &block)
293 def register_by_email_activation(user, &block)
293 token = Token.new(:user => user, :action => "register")
294 token = Token.new(:user => user, :action => "register")
294 if user.save and token.save
295 if user.save and token.save
295 Mailer.register(token).deliver
296 Mailer.register(token).deliver
296 flash[:notice] = l(:notice_account_register_done, :email => ERB::Util.h(user.mail))
297 flash[:notice] = l(:notice_account_register_done, :email => ERB::Util.h(user.mail))
297 redirect_to signin_path
298 redirect_to signin_path
298 else
299 else
299 yield if block_given?
300 yield if block_given?
300 end
301 end
301 end
302 end
302
303
303 # Automatically register a user
304 # Automatically register a user
304 #
305 #
305 # Pass a block for behavior when a user fails to save
306 # Pass a block for behavior when a user fails to save
306 def register_automatically(user, &block)
307 def register_automatically(user, &block)
307 # Automatic activation
308 # Automatic activation
308 user.activate
309 user.activate
309 user.last_login_on = Time.now
310 user.last_login_on = Time.now
310 if user.save
311 if user.save
311 self.logged_user = user
312 self.logged_user = user
312 flash[:notice] = l(:notice_account_activated)
313 flash[:notice] = l(:notice_account_activated)
313 redirect_to my_account_path
314 redirect_to my_account_path
314 else
315 else
315 yield if block_given?
316 yield if block_given?
316 end
317 end
317 end
318 end
318
319
319 # Manual activation by the administrator
320 # Manual activation by the administrator
320 #
321 #
321 # Pass a block for behavior when a user fails to save
322 # Pass a block for behavior when a user fails to save
322 def register_manually_by_administrator(user, &block)
323 def register_manually_by_administrator(user, &block)
323 if user.save
324 if user.save
324 # Sends an email to the administrators
325 # Sends an email to the administrators
325 Mailer.account_activation_request(user).deliver
326 Mailer.account_activation_request(user).deliver
326 account_pending(user)
327 account_pending(user)
327 else
328 else
328 yield if block_given?
329 yield if block_given?
329 end
330 end
330 end
331 end
331
332
332 def handle_inactive_user(user, redirect_path=signin_path)
333 def handle_inactive_user(user, redirect_path=signin_path)
333 if user.registered?
334 if user.registered?
334 account_pending(user, redirect_path)
335 account_pending(user, redirect_path)
335 else
336 else
336 account_locked(user, redirect_path)
337 account_locked(user, redirect_path)
337 end
338 end
338 end
339 end
339
340
340 def account_pending(user, redirect_path=signin_path)
341 def account_pending(user, redirect_path=signin_path)
341 if Setting.self_registration == '1'
342 if Setting.self_registration == '1'
342 flash[:error] = l(:notice_account_not_activated_yet, :url => activation_email_path)
343 flash[:error] = l(:notice_account_not_activated_yet, :url => activation_email_path)
343 session[:registered_user_id] = user.id
344 session[:registered_user_id] = user.id
344 else
345 else
345 flash[:error] = l(:notice_account_pending)
346 flash[:error] = l(:notice_account_pending)
346 end
347 end
347 redirect_to redirect_path
348 redirect_to redirect_path
348 end
349 end
349
350
350 def account_locked(user, redirect_path=signin_path)
351 def account_locked(user, redirect_path=signin_path)
351 flash[:error] = l(:notice_account_locked)
352 flash[:error] = l(:notice_account_locked)
352 redirect_to redirect_path
353 redirect_to redirect_path
353 end
354 end
354 end
355 end
@@ -1,164 +1,191
1 require File.expand_path('../../test_helper', __FILE__)
1 require File.expand_path('../../test_helper', __FILE__)
2
2
3 class SudoModeTest < Redmine::IntegrationTest
3 class SudoModeTest < Redmine::IntegrationTest
4 fixtures :projects, :members, :member_roles, :roles, :users, :email_addresses
4 fixtures :projects, :members, :member_roles, :roles, :users, :email_addresses
5
5
6 def setup
6 def setup
7 Redmine::SudoMode.stubs(:enabled?).returns(true)
7 Redmine::SudoMode.stubs(:enabled?).returns(true)
8 end
8 end
9
9
10 def test_sudo_mode_should_be_active_after_login
11 log_user("admin", "admin")
12 get "/users/new"
13 assert_response :success
14 post "/users",
15 :user => { :login => "psmith", :firstname => "Paul",
16 :lastname => "Smith", :mail => "psmith@somenet.foo",
17 :language => "en", :password => "psmith09",
18 :password_confirmation => "psmith09" }
19 assert_response 302
20
21 user = User.find_by_login("psmith")
22 assert_kind_of User, user
23 end
24
10 def test_add_user
25 def test_add_user
11 log_user("admin", "admin")
26 log_user("admin", "admin")
27 expire_sudo_mode!
12 get "/users/new"
28 get "/users/new"
13 assert_response :success
29 assert_response :success
14 post "/users",
30 post "/users",
15 :user => { :login => "psmith", :firstname => "Paul",
31 :user => { :login => "psmith", :firstname => "Paul",
16 :lastname => "Smith", :mail => "psmith@somenet.foo",
32 :lastname => "Smith", :mail => "psmith@somenet.foo",
17 :language => "en", :password => "psmith09",
33 :language => "en", :password => "psmith09",
18 :password_confirmation => "psmith09" }
34 :password_confirmation => "psmith09" }
19 assert_response :success
35 assert_response :success
20 assert_nil User.find_by_login("psmith")
36 assert_nil User.find_by_login("psmith")
21
37
22 assert_select 'input[name=?][value=?]', 'user[login]', 'psmith'
38 assert_select 'input[name=?][value=?]', 'user[login]', 'psmith'
23 assert_select 'input[name=?][value=?]', 'user[firstname]', 'Paul'
39 assert_select 'input[name=?][value=?]', 'user[firstname]', 'Paul'
24
40
25 post "/users",
41 post "/users",
26 :user => { :login => "psmith", :firstname => "Paul",
42 :user => { :login => "psmith", :firstname => "Paul",
27 :lastname => "Smith", :mail => "psmith@somenet.foo",
43 :lastname => "Smith", :mail => "psmith@somenet.foo",
28 :language => "en", :password => "psmith09",
44 :language => "en", :password => "psmith09",
29 :password_confirmation => "psmith09" },
45 :password_confirmation => "psmith09" },
30 :sudo_password => 'admin'
46 :sudo_password => 'admin'
31 assert_response 302
47 assert_response 302
32
48
33 user = User.find_by_login("psmith")
49 user = User.find_by_login("psmith")
34 assert_kind_of User, user
50 assert_kind_of User, user
35 end
51 end
36
52
37 def test_create_member_xhr
53 def test_create_member_xhr
38 log_user 'admin', 'admin'
54 log_user 'admin', 'admin'
55 expire_sudo_mode!
39 get '/projects/ecookbook/settings/members'
56 get '/projects/ecookbook/settings/members'
40 assert_response :success
57 assert_response :success
41
58
42 assert_no_difference 'Member.count' do
59 assert_no_difference 'Member.count' do
43 xhr :post, '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}
60 xhr :post, '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}
44 end
61 end
45
62
46 assert_no_difference 'Member.count' do
63 assert_no_difference 'Member.count' do
47 xhr :post, '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: ''
64 xhr :post, '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: ''
48 end
65 end
49
66
50 assert_no_difference 'Member.count' do
67 assert_no_difference 'Member.count' do
51 xhr :post, '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: 'wrong'
68 xhr :post, '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: 'wrong'
52 end
69 end
53
70
54 assert_difference 'Member.count' do
71 assert_difference 'Member.count' do
55 xhr :post, '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: 'admin'
72 xhr :post, '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: 'admin'
56 end
73 end
57 assert User.find(7).member_of?(Project.find(1))
74 assert User.find(7).member_of?(Project.find(1))
58 end
75 end
59
76
60 def test_create_member
77 def test_create_member
61 log_user 'admin', 'admin'
78 log_user 'admin', 'admin'
79 expire_sudo_mode!
62 get '/projects/ecookbook/settings/members'
80 get '/projects/ecookbook/settings/members'
63 assert_response :success
81 assert_response :success
64
82
65 assert_no_difference 'Member.count' do
83 assert_no_difference 'Member.count' do
66 post '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}
84 post '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}
67 end
85 end
68
86
69 assert_no_difference 'Member.count' do
87 assert_no_difference 'Member.count' do
70 post '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: ''
88 post '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: ''
71 end
89 end
72
90
73 assert_no_difference 'Member.count' do
91 assert_no_difference 'Member.count' do
74 post '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: 'wrong'
92 post '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: 'wrong'
75 end
93 end
76
94
77 assert_difference 'Member.count' do
95 assert_difference 'Member.count' do
78 post '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: 'admin'
96 post '/projects/ecookbook/memberships', membership: {role_ids: [1], user_id: 7}, sudo_password: 'admin'
79 end
97 end
80
98
81 assert_redirected_to '/projects/ecookbook/settings/members'
99 assert_redirected_to '/projects/ecookbook/settings/members'
82 assert User.find(7).member_of?(Project.find(1))
100 assert User.find(7).member_of?(Project.find(1))
83 end
101 end
84
102
85 def test_create_role
103 def test_create_role
86 log_user 'admin', 'admin'
104 log_user 'admin', 'admin'
105 expire_sudo_mode!
87 get '/roles'
106 get '/roles'
88 assert_response :success
107 assert_response :success
89
108
90 get '/roles/new'
109 get '/roles/new'
91 assert_response :success
110 assert_response :success
92
111
93 post '/roles', role: { }
112 post '/roles', role: { }
94 assert_response :success
113 assert_response :success
95 assert_select 'h2', 'Confirm your password to continue'
114 assert_select 'h2', 'Confirm your password to continue'
96 assert_select 'form[action="/roles"]'
115 assert_select 'form[action="/roles"]'
97 assert assigns(:sudo_form).errors.blank?
116 assert assigns(:sudo_form).errors.blank?
98
117
99 post '/roles', role: { name: 'new role', issues_visibility: 'all' }
118 post '/roles', role: { name: 'new role', issues_visibility: 'all' }
100 assert_response :success
119 assert_response :success
101 assert_select 'h2', 'Confirm your password to continue'
120 assert_select 'h2', 'Confirm your password to continue'
102 assert_select 'form[action="/roles"]'
121 assert_select 'form[action="/roles"]'
103 assert_match /"new role"/, response.body
122 assert_match /"new role"/, response.body
104 assert assigns(:sudo_form).errors.blank?
123 assert assigns(:sudo_form).errors.blank?
105
124
106 post '/roles', role: { name: 'new role', issues_visibility: 'all' }, sudo_password: 'wrong'
125 post '/roles', role: { name: 'new role', issues_visibility: 'all' }, sudo_password: 'wrong'
107 assert_response :success
126 assert_response :success
108 assert_select 'h2', 'Confirm your password to continue'
127 assert_select 'h2', 'Confirm your password to continue'
109 assert_select 'form[action="/roles"]'
128 assert_select 'form[action="/roles"]'
110 assert_match /"new role"/, response.body
129 assert_match /"new role"/, response.body
111 assert assigns(:sudo_form).errors[:password].present?
130 assert assigns(:sudo_form).errors[:password].present?
112
131
113 assert_difference 'Role.count' do
132 assert_difference 'Role.count' do
114 post '/roles', role: { name: 'new role', issues_visibility: 'all', assignable: '1', permissions: %w(view_calendar) }, sudo_password: 'admin'
133 post '/roles', role: { name: 'new role', issues_visibility: 'all', assignable: '1', permissions: %w(view_calendar) }, sudo_password: 'admin'
115 end
134 end
116 assert_redirected_to '/roles'
135 assert_redirected_to '/roles'
117 end
136 end
118
137
119 def test_update_email_address
138 def test_update_email_address
120 log_user 'jsmith', 'jsmith'
139 log_user 'jsmith', 'jsmith'
140 expire_sudo_mode!
121 get '/my/account'
141 get '/my/account'
122 assert_response :success
142 assert_response :success
123 post '/my/account', user: { mail: 'newmail@test.com' }
143 post '/my/account', user: { mail: 'newmail@test.com' }
124 assert_response :success
144 assert_response :success
125 assert_select 'h2', 'Confirm your password to continue'
145 assert_select 'h2', 'Confirm your password to continue'
126 assert_select 'form[action="/my/account"]'
146 assert_select 'form[action="/my/account"]'
127 assert_match /"newmail@test\.com"/, response.body
147 assert_match /"newmail@test\.com"/, response.body
128 assert assigns(:sudo_form).errors.blank?
148 assert assigns(:sudo_form).errors.blank?
129
149
130 # wrong password
150 # wrong password
131 post '/my/account', user: { mail: 'newmail@test.com' }, sudo_password: 'wrong'
151 post '/my/account', user: { mail: 'newmail@test.com' }, sudo_password: 'wrong'
132 assert_response :success
152 assert_response :success
133 assert_select 'h2', 'Confirm your password to continue'
153 assert_select 'h2', 'Confirm your password to continue'
134 assert_select 'form[action="/my/account"]'
154 assert_select 'form[action="/my/account"]'
135 assert_match /"newmail@test\.com"/, response.body
155 assert_match /"newmail@test\.com"/, response.body
136 assert assigns(:sudo_form).errors[:password].present?
156 assert assigns(:sudo_form).errors[:password].present?
137
157
138 # correct password
158 # correct password
139 post '/my/account', user: { mail: 'newmail@test.com' }, sudo_password: 'jsmith'
159 post '/my/account', user: { mail: 'newmail@test.com' }, sudo_password: 'jsmith'
140 assert_redirected_to '/my/account'
160 assert_redirected_to '/my/account'
141 assert_equal 'newmail@test.com', User.find_by_login('jsmith').mail
161 assert_equal 'newmail@test.com', User.find_by_login('jsmith').mail
142
162
143 # sudo mode should now be active and not require password again
163 # sudo mode should now be active and not require password again
144 post '/my/account', user: { mail: 'even.newer.mail@test.com' }
164 post '/my/account', user: { mail: 'even.newer.mail@test.com' }
145 assert_redirected_to '/my/account'
165 assert_redirected_to '/my/account'
146 assert_equal 'even.newer.mail@test.com', User.find_by_login('jsmith').mail
166 assert_equal 'even.newer.mail@test.com', User.find_by_login('jsmith').mail
147 end
167 end
148
168
149 def test_sudo_mode_should_skip_api_requests
169 def test_sudo_mode_should_skip_api_requests
150 with_settings :rest_api_enabled => '1' do
170 with_settings :rest_api_enabled => '1' do
151 assert_difference('User.count') do
171 assert_difference('User.count') do
152 post '/users.json', {
172 post '/users.json', {
153 :user => {
173 :user => {
154 :login => 'foo', :firstname => 'Firstname', :lastname => 'Lastname',
174 :login => 'foo', :firstname => 'Firstname', :lastname => 'Lastname',
155 :mail => 'foo@example.net', :password => 'secret123',
175 :mail => 'foo@example.net', :password => 'secret123',
156 :mail_notification => 'only_assigned'}
176 :mail_notification => 'only_assigned'}
157 },
177 },
158 credentials('admin')
178 credentials('admin')
159
179
160 assert_response :created
180 assert_response :created
161 end
181 end
162 end
182 end
163 end
183 end
184
185 private
186
187 # sudo mode is active after sign, let it expire by advancing the time
188 def expire_sudo_mode!
189 travel_to 20.minutes.from_now
190 end
164 end
191 end
General Comments 0
You need to be logged in to leave comments. Login now