Move the user api methods into a separate controller in the api namespace
[rails.git] / test / controllers / users_controller_test.rb
1 require "test_helper"
2
3 class UsersControllerTest < ActionController::TestCase
4   def setup
5     stub_hostip_requests
6   end
7
8   ##
9   # test all routes which lead to this controller
10   def test_routes
11     assert_routing(
12       { :path => "/login", :method => :get },
13       { :controller => "users", :action => "login" }
14     )
15     assert_routing(
16       { :path => "/login", :method => :post },
17       { :controller => "users", :action => "login" }
18     )
19     assert_recognizes(
20       { :controller => "users", :action => "login", :format => "html" },
21       { :path => "/login.html", :method => :get }
22     )
23
24     assert_routing(
25       { :path => "/logout", :method => :get },
26       { :controller => "users", :action => "logout" }
27     )
28     assert_routing(
29       { :path => "/logout", :method => :post },
30       { :controller => "users", :action => "logout" }
31     )
32     assert_recognizes(
33       { :controller => "users", :action => "logout", :format => "html" },
34       { :path => "/logout.html", :method => :get }
35     )
36
37     assert_routing(
38       { :path => "/user/new", :method => :get },
39       { :controller => "users", :action => "new" }
40     )
41
42     assert_routing(
43       { :path => "/user/new", :method => :post },
44       { :controller => "users", :action => "create" }
45     )
46
47     assert_routing(
48       { :path => "/user/terms", :method => :get },
49       { :controller => "users", :action => "terms" }
50     )
51
52     assert_routing(
53       { :path => "/user/save", :method => :post },
54       { :controller => "users", :action => "save" }
55     )
56
57     assert_routing(
58       { :path => "/user/username/confirm", :method => :get },
59       { :controller => "users", :action => "confirm", :display_name => "username" }
60     )
61     assert_routing(
62       { :path => "/user/username/confirm", :method => :post },
63       { :controller => "users", :action => "confirm", :display_name => "username" }
64     )
65     assert_routing(
66       { :path => "/user/username/confirm/resend", :method => :get },
67       { :controller => "users", :action => "confirm_resend", :display_name => "username" }
68     )
69
70     assert_routing(
71       { :path => "/user/confirm", :method => :get },
72       { :controller => "users", :action => "confirm" }
73     )
74     assert_routing(
75       { :path => "/user/confirm", :method => :post },
76       { :controller => "users", :action => "confirm" }
77     )
78     assert_routing(
79       { :path => "/user/confirm-email", :method => :get },
80       { :controller => "users", :action => "confirm_email" }
81     )
82     assert_routing(
83       { :path => "/user/confirm-email", :method => :post },
84       { :controller => "users", :action => "confirm_email" }
85     )
86
87     assert_routing(
88       { :path => "/user/go_public", :method => :post },
89       { :controller => "users", :action => "go_public" }
90     )
91
92     assert_routing(
93       { :path => "/user/forgot-password", :method => :get },
94       { :controller => "users", :action => "lost_password" }
95     )
96     assert_routing(
97       { :path => "/user/forgot-password", :method => :post },
98       { :controller => "users", :action => "lost_password" }
99     )
100     assert_routing(
101       { :path => "/user/reset-password", :method => :get },
102       { :controller => "users", :action => "reset_password" }
103     )
104     assert_routing(
105       { :path => "/user/reset-password", :method => :post },
106       { :controller => "users", :action => "reset_password" }
107     )
108
109     assert_routing(
110       { :path => "/user/suspended", :method => :get },
111       { :controller => "users", :action => "suspended" }
112     )
113
114     assert_routing(
115       { :path => "/user/username", :method => :get },
116       { :controller => "users", :action => "show", :display_name => "username" }
117     )
118
119     assert_routing(
120       { :path => "/user/username/account", :method => :get },
121       { :controller => "users", :action => "account", :display_name => "username" }
122     )
123     assert_routing(
124       { :path => "/user/username/account", :method => :post },
125       { :controller => "users", :action => "account", :display_name => "username" }
126     )
127
128     assert_routing(
129       { :path => "/user/username/make_friend", :method => :get },
130       { :controller => "users", :action => "make_friend", :display_name => "username" }
131     )
132     assert_routing(
133       { :path => "/user/username/make_friend", :method => :post },
134       { :controller => "users", :action => "make_friend", :display_name => "username" }
135     )
136     assert_routing(
137       { :path => "/user/username/remove_friend", :method => :get },
138       { :controller => "users", :action => "remove_friend", :display_name => "username" }
139     )
140     assert_routing(
141       { :path => "/user/username/remove_friend", :method => :post },
142       { :controller => "users", :action => "remove_friend", :display_name => "username" }
143     )
144
145     assert_routing(
146       { :path => "/user/username/set_status", :method => :get },
147       { :controller => "users", :action => "set_status", :display_name => "username" }
148     )
149     assert_routing(
150       { :path => "/user/username/delete", :method => :get },
151       { :controller => "users", :action => "delete", :display_name => "username" }
152     )
153
154     assert_routing(
155       { :path => "/users", :method => :get },
156       { :controller => "users", :action => "index" }
157     )
158     assert_routing(
159       { :path => "/users", :method => :post },
160       { :controller => "users", :action => "index" }
161     )
162     assert_routing(
163       { :path => "/users/status", :method => :get },
164       { :controller => "users", :action => "index", :status => "status" }
165     )
166     assert_routing(
167       { :path => "/users/status", :method => :post },
168       { :controller => "users", :action => "index", :status => "status" }
169     )
170   end
171
172   # The user creation page loads
173   def test_new_view
174     get :new
175     assert_response :redirect
176     assert_redirected_to user_new_path(:cookie_test => "true")
177
178     get :new, :params => { :cookie_test => "true" }, :session => { :cookie_test => true }
179     assert_response :success
180
181     assert_select "html", :count => 1 do
182       assert_select "head", :count => 1 do
183         assert_select "title", :text => /Sign Up/, :count => 1
184       end
185       assert_select "body", :count => 1 do
186         assert_select "div#content", :count => 1 do
187           assert_select "form[action='/user/new'][method='post']", :count => 1 do
188             assert_select "input[id='user_email']", :count => 1
189             assert_select "input[id='user_email_confirmation']", :count => 1
190             assert_select "input[id='user_display_name']", :count => 1
191             assert_select "input[id='user_pass_crypt'][type='password']", :count => 1
192             assert_select "input[id='user_pass_crypt_confirmation'][type='password']", :count => 1
193             assert_select "input[type='submit'][value='Sign Up']", :count => 1
194           end
195         end
196       end
197     end
198   end
199
200   def test_new_view_logged_in
201     session[:user] = create(:user).id
202
203     get :new
204     assert_response :redirect
205     assert_redirected_to user_new_path(:cookie_test => "true")
206     get :new, :params => { :cookie_test => "true" }
207     assert_response :redirect
208     assert_redirected_to root_path
209
210     get :new, :params => { :referer => "/test" }
211     assert_response :redirect
212     assert_redirected_to user_new_path(:referer => "/test", :cookie_test => "true")
213     get :new, :params => { :referer => "/test", :cookie_test => "true" }
214     assert_response :redirect
215     assert_redirected_to "/test"
216   end
217
218   def test_new_success
219     user = build(:user, :pending)
220
221     assert_difference "User.count", 1 do
222       assert_difference "ActionMailer::Base.deliveries.size", 1 do
223         perform_enqueued_jobs do
224           post :save, :session => { :new_user => user }
225         end
226       end
227     end
228
229     # Check the e-mail
230     register_email = ActionMailer::Base.deliveries.first
231
232     assert_equal register_email.to[0], user.email
233     assert_match(/#{@url}/, register_email.body.to_s)
234
235     # Check the page
236     assert_redirected_to :action => "confirm", :display_name => user.display_name
237
238     ActionMailer::Base.deliveries.clear
239   end
240
241   def test_new_duplicate_email
242     user = build(:user, :pending)
243     user.email = create(:user).email
244
245     assert_no_difference "User.count" do
246       assert_no_difference "ActionMailer::Base.deliveries.size" do
247         perform_enqueued_jobs do
248           post :save, :session => { :new_user => user }
249         end
250       end
251     end
252
253     assert_response :success
254     assert_template "new"
255     assert_select "form > fieldset > div.form-row > input.field_with_errors#user_email"
256   end
257
258   def test_new_duplicate_email_uppercase
259     user = build(:user, :pending)
260     user.email = create(:user).email.upcase
261
262     assert_no_difference "User.count" do
263       assert_no_difference "ActionMailer::Base.deliveries.size" do
264         perform_enqueued_jobs do
265           post :save, :session => { :new_user => user }
266         end
267       end
268     end
269
270     assert_response :success
271     assert_template "new"
272     assert_select "form > fieldset > div.form-row > input.field_with_errors#user_email"
273   end
274
275   def test_new_duplicate_name
276     user = build(:user, :pending)
277     user.display_name = create(:user).display_name
278
279     assert_no_difference "User.count" do
280       assert_no_difference "ActionMailer::Base.deliveries.size" do
281         perform_enqueued_jobs do
282           post :save, :session => { :new_user => user }
283         end
284       end
285     end
286
287     assert_response :success
288     assert_template "new"
289     assert_select "form > fieldset > div.form-row > input.field_with_errors#user_display_name"
290   end
291
292   def test_new_duplicate_name_uppercase
293     user = build(:user, :pending)
294     user.display_name = create(:user).display_name.upcase
295
296     assert_no_difference "User.count" do
297       assert_no_difference "ActionMailer::Base.deliveries.size" do
298         perform_enqueued_jobs do
299           post :save, :session => { :new_user => user }
300         end
301       end
302     end
303
304     assert_response :success
305     assert_template "new"
306     assert_select "form > fieldset > div.form-row > input.field_with_errors#user_display_name"
307   end
308
309   def test_new_blocked_domain
310     user = build(:user, :pending, :email => "user@example.net")
311     create(:acl, :domain => "example.net", :k => "no_account_creation")
312
313     assert_no_difference "User.count" do
314       assert_no_difference "ActionMailer::Base.deliveries.size" do
315         perform_enqueued_jobs do
316           post :save, :session => { :new_user => user }
317         end
318       end
319     end
320
321     assert_response :success
322     assert_template "blocked"
323   end
324
325   def test_save_referer_params
326     user = build(:user, :pending)
327
328     assert_difference "User.count", 1 do
329       assert_difference "ActionMailer::Base.deliveries.size", 1 do
330         perform_enqueued_jobs do
331           post :save, :session => { :new_user => user,
332                                     :referer => "/edit?editor=id#map=1/2/3" }
333         end
334       end
335     end
336
337     assert_equal welcome_path(:editor => "id", :zoom => 1, :lat => 2, :lon => 3),
338                  user.tokens.order("id DESC").first.referer
339
340     ActionMailer::Base.deliveries.clear
341   end
342
343   def test_logout_without_referer
344     get :logout
345     assert_response :success
346     assert_template :logout
347     assert_select "input[name=referer][value=?]", ""
348
349     session_id = assert_select("input[name=session]").first["value"]
350
351     get :logout, :params => { :session => session_id }
352     assert_response :redirect
353     assert_redirected_to root_path
354   end
355
356   def test_logout_with_referer
357     get :logout, :params => { :referer => "/test" }
358     assert_response :success
359     assert_template :logout
360     assert_select "input[name=referer][value=?]", "/test"
361
362     session_id = assert_select("input[name=session]").first["value"]
363
364     get :logout, :params => { :session => session_id, :referer => "/test" }
365     assert_response :redirect
366     assert_redirected_to "/test"
367   end
368
369   def test_logout_with_token
370     token = create(:user).tokens.create
371
372     session[:token] = token.token
373
374     get :logout
375     assert_response :success
376     assert_template :logout
377     assert_select "input[name=referer][value=?]", ""
378     assert_equal token.token, session[:token]
379     assert_not_nil UserToken.where(:id => token.id).first
380
381     session_id = assert_select("input[name=session]").first["value"]
382
383     get :logout, :params => { :session => session_id }
384     assert_response :redirect
385     assert_redirected_to root_path
386     assert_nil session[:token]
387     assert_nil UserToken.where(:id => token.id).first
388   end
389
390   def test_confirm_get
391     user = create(:user, :pending)
392     confirm_string = user.tokens.create.token
393
394     @request.cookies["_osm_session"] = user.display_name
395     get :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }
396     assert_response :success
397     assert_template :confirm
398   end
399
400   def test_confirm_get_already_confirmed
401     user = create(:user)
402     confirm_string = user.tokens.create.token
403
404     @request.cookies["_osm_session"] = user.display_name
405     get :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }
406     assert_response :redirect
407     assert_redirected_to root_path
408   end
409
410   def test_confirm_success_no_token_no_referer
411     user = create(:user, :pending)
412     stub_gravatar_request(user.email)
413     confirm_string = user.tokens.create.token
414
415     @request.cookies["_osm_session"] = user.display_name
416     post :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }
417     assert_redirected_to login_path
418     assert_match(/Confirmed your account/, flash[:notice])
419   end
420
421   def test_confirm_success_good_token_no_referer
422     user = create(:user, :pending)
423     stub_gravatar_request(user.email)
424     confirm_string = user.tokens.create.token
425     token = user.tokens.create.token
426
427     @request.cookies["_osm_session"] = user.display_name
428     post :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }, :session => { :token => token }
429     assert_redirected_to welcome_path
430   end
431
432   def test_confirm_success_bad_token_no_referer
433     user = create(:user, :pending)
434     stub_gravatar_request(user.email)
435     confirm_string = user.tokens.create.token
436     token = create(:user).tokens.create.token
437
438     @request.cookies["_osm_session"] = user.display_name
439     post :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }, :session => { :token => token }
440     assert_redirected_to login_path
441     assert_match(/Confirmed your account/, flash[:notice])
442   end
443
444   def test_confirm_success_no_token_with_referer
445     user = create(:user, :pending)
446     stub_gravatar_request(user.email)
447     confirm_string = user.tokens.create(:referer => diary_new_path).token
448
449     @request.cookies["_osm_session"] = user.display_name
450     post :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }
451     assert_redirected_to login_path(:referer => diary_new_path)
452     assert_match(/Confirmed your account/, flash[:notice])
453   end
454
455   def test_confirm_success_good_token_with_referer
456     user = create(:user, :pending)
457     stub_gravatar_request(user.email)
458     confirm_string = user.tokens.create(:referer => diary_new_path).token
459     token = user.tokens.create.token
460
461     @request.cookies["_osm_session"] = user.display_name
462     post :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }, :session => { :token => token }
463     assert_redirected_to diary_new_path
464   end
465
466   def test_confirm_success_bad_token_with_referer
467     user = create(:user, :pending)
468     stub_gravatar_request(user.email)
469     confirm_string = user.tokens.create(:referer => diary_new_path).token
470     token = create(:user).tokens.create.token
471
472     @request.cookies["_osm_session"] = user.display_name
473     post :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }, :session => { :token => token }
474     assert_redirected_to login_path(:referer => diary_new_path)
475     assert_match(/Confirmed your account/, flash[:notice])
476   end
477
478   def test_confirm_expired_token
479     user = create(:user, :pending)
480     confirm_string = user.tokens.create(:expiry => 1.day.ago).token
481
482     @request.cookies["_osm_session"] = user.display_name
483     post :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }
484     assert_redirected_to :action => "confirm"
485     assert_match(/confirmation code has expired/, flash[:error])
486   end
487
488   def test_confirm_already_confirmed
489     user = create(:user)
490     confirm_string = user.tokens.create(:referer => diary_new_path).token
491
492     @request.cookies["_osm_session"] = user.display_name
493     post :confirm, :params => { :display_name => user.display_name, :confirm_string => confirm_string }
494     assert_redirected_to :action => "login"
495     assert_match(/already been confirmed/, flash[:error])
496   end
497
498   def test_confirm_resend_success
499     user = create(:user, :pending)
500     session[:token] = user.tokens.create.token
501
502     assert_difference "ActionMailer::Base.deliveries.size", 1 do
503       perform_enqueued_jobs do
504         get :confirm_resend, :params => { :display_name => user.display_name }
505       end
506     end
507
508     assert_response :redirect
509     assert_redirected_to login_path
510     assert_match(/sent a new confirmation/, flash[:notice])
511
512     email = ActionMailer::Base.deliveries.last
513
514     assert_equal user.email, email.to.first
515
516     ActionMailer::Base.deliveries.clear
517   end
518
519   def test_confirm_resend_no_token
520     user = create(:user, :pending)
521     assert_no_difference "ActionMailer::Base.deliveries.size" do
522       perform_enqueued_jobs do
523         get :confirm_resend, :params => { :display_name => user.display_name }
524       end
525     end
526
527     assert_response :redirect
528     assert_redirected_to login_path
529     assert_match "User #{user.display_name} not found.", flash[:error]
530   end
531
532   def test_confirm_resend_unknown_user
533     assert_no_difference "ActionMailer::Base.deliveries.size" do
534       perform_enqueued_jobs do
535         get :confirm_resend, :params => { :display_name => "No Such User" }
536       end
537     end
538
539     assert_response :redirect
540     assert_redirected_to login_path
541     assert_match "User No Such User not found.", flash[:error]
542   end
543
544   def test_confirm_email_get
545     user = create(:user)
546     confirm_string = user.tokens.create.token
547
548     get :confirm_email, :params => { :confirm_string => confirm_string }
549     assert_response :success
550     assert_template :confirm_email
551   end
552
553   def test_confirm_email_success
554     user = create(:user, :new_email => "test-new@example.com")
555     stub_gravatar_request(user.new_email)
556     confirm_string = user.tokens.create.token
557
558     post :confirm_email, :params => { :confirm_string => confirm_string }
559     assert_response :redirect
560     assert_redirected_to :action => :account, :display_name => user.display_name
561     assert_match(/Confirmed your change of email address/, flash[:notice])
562   end
563
564   def test_confirm_email_already_confirmed
565     user = create(:user)
566     confirm_string = user.tokens.create.token
567
568     post :confirm_email, :params => { :confirm_string => confirm_string }
569     assert_response :redirect
570     assert_redirected_to :action => :account, :display_name => user.display_name
571     assert_match(/already been confirmed/, flash[:error])
572   end
573
574   def test_confirm_email_bad_token
575     post :confirm_email, :params => { :confirm_string => "XXXXX" }
576     assert_response :success
577     assert_template :confirm_email
578     assert_match(/confirmation code has expired or does not exist/, flash[:error])
579   end
580
581   ##
582   # test if testing for a gravatar works
583   # this happens when the email is actually changed
584   # which is triggered by the confirmation mail
585   def test_gravatar_auto_enable
586     # switch to email that has a gravatar
587     user = create(:user, :new_email => "test-new@example.com")
588     stub_gravatar_request(user.new_email, 200)
589     confirm_string = user.tokens.create.token
590     # precondition gravatar should be turned off
591     assert_not user.image_use_gravatar
592     post :confirm_email, :params => { :confirm_string => confirm_string }
593     assert_response :redirect
594     assert_redirected_to :action => :account, :display_name => user.display_name
595     assert_match(/Confirmed your change of email address/, flash[:notice])
596     # gravatar use should now be enabled
597     assert User.find(user.id).image_use_gravatar
598   end
599
600   def test_gravatar_auto_disable
601     # switch to email without a gravatar
602     user = create(:user, :new_email => "test-new@example.com", :image_use_gravatar => true)
603     stub_gravatar_request(user.new_email, 404)
604     confirm_string = user.tokens.create.token
605     # precondition gravatar should be turned on
606     assert user.image_use_gravatar
607     post :confirm_email, :params => { :confirm_string => confirm_string }
608     assert_response :redirect
609     assert_redirected_to :action => :account, :display_name => user.display_name
610     assert_match(/Confirmed your change of email address/, flash[:notice])
611     # gravatar use should now be disabled
612     assert_not User.find(user.id).image_use_gravatar
613   end
614
615   def test_terms_new_user
616     get :terms, :session => { :new_user => User.new }
617     assert_response :success
618     assert_template :terms
619   end
620
621   def test_terms_agreed
622     user = create(:user, :terms_seen => true, :terms_agreed => Date.yesterday)
623
624     session[:user] = user.id
625
626     get :terms
627     assert_response :redirect
628     assert_redirected_to :action => :account, :display_name => user.display_name
629   end
630
631   def test_terms_not_seen_without_referer
632     user = create(:user, :terms_seen => false, :terms_agreed => nil)
633
634     session[:user] = user.id
635
636     get :terms
637     assert_response :success
638     assert_template :terms
639
640     post :save, :params => { :user => { :consider_pd => true } }
641     assert_response :redirect
642     assert_redirected_to :action => :account, :display_name => user.display_name
643     assert_equal "Thanks for accepting the new contributor terms!", flash[:notice]
644
645     user.reload
646
647     assert_equal true, user.consider_pd
648     assert_not_nil user.terms_agreed
649     assert_equal true, user.terms_seen
650   end
651
652   def test_terms_not_seen_with_referer
653     user = create(:user, :terms_seen => false, :terms_agreed => nil)
654
655     session[:user] = user.id
656
657     get :terms, :params => { :referer => "/test" }
658     assert_response :success
659     assert_template :terms
660
661     post :save, :params => { :user => { :consider_pd => true }, :referer => "/test" }
662     assert_response :redirect
663     assert_redirected_to "/test"
664     assert_equal "Thanks for accepting the new contributor terms!", flash[:notice]
665
666     user.reload
667
668     assert_equal true, user.consider_pd
669     assert_not_nil user.terms_agreed
670     assert_equal true, user.terms_seen
671   end
672
673   # Check that if you haven't seen the terms, and make a request that requires authentication,
674   # that your request is redirected to view the terms
675   def test_terms_not_seen_redirection
676     user = create(:user, :terms_seen => false, :terms_agreed => nil)
677     session[:user] = user.id
678
679     get :account, :params => { :display_name => user.display_name }
680     assert_response :redirect
681     assert_redirected_to :action => :terms, :referer => "/user/#{ERB::Util.u(user.display_name)}/account"
682   end
683
684   def test_go_public
685     user = create(:user, :data_public => false)
686     post :go_public, :session => { :user => user }
687     assert_response :redirect
688     assert_redirected_to :action => :account, :display_name => user.display_name
689     assert_equal true, User.find(user.id).data_public
690   end
691
692   def test_lost_password
693     # Test fetching the lost password page
694     get :lost_password
695     assert_response :success
696     assert_template :lost_password
697     assert_select "div#notice", false
698
699     # Test resetting using the address as recorded for a user that has an
700     # address which is duplicated in a different case by another user
701     user = create(:user)
702     uppercase_user = build(:user, :email => user.email.upcase).tap { |u| u.save(:validate => false) }
703
704     assert_difference "ActionMailer::Base.deliveries.size", 1 do
705       perform_enqueued_jobs do
706         post :lost_password, :params => { :user => { :email => user.email } }
707       end
708     end
709     assert_response :redirect
710     assert_redirected_to :action => :login
711     assert_match(/^Sorry you lost it/, flash[:notice])
712     email = ActionMailer::Base.deliveries.first
713     assert_equal 1, email.to.count
714     assert_equal user.email, email.to.first
715     ActionMailer::Base.deliveries.clear
716
717     # Test resetting using an address that matches a different user
718     # that has the same address in a different case
719     assert_difference "ActionMailer::Base.deliveries.size", 1 do
720       perform_enqueued_jobs do
721         post :lost_password, :params => { :user => { :email => user.email.upcase } }
722       end
723     end
724     assert_response :redirect
725     assert_redirected_to :action => :login
726     assert_match(/^Sorry you lost it/, flash[:notice])
727     email = ActionMailer::Base.deliveries.first
728     assert_equal 1, email.to.count
729     assert_equal uppercase_user.email, email.to.first
730     ActionMailer::Base.deliveries.clear
731
732     # Test resetting using an address that is a case insensitive match
733     # for more than one user but not an exact match for either
734     assert_no_difference "ActionMailer::Base.deliveries.size" do
735       perform_enqueued_jobs do
736         post :lost_password, :params => { :user => { :email => user.email.titlecase } }
737       end
738     end
739     assert_response :success
740     assert_template :lost_password
741     assert_select ".error", /^Could not find that email address/
742
743     # Test resetting using the address as recorded for a user that has an
744     # address which is case insensitively unique
745     third_user = create(:user)
746     assert_difference "ActionMailer::Base.deliveries.size", 1 do
747       perform_enqueued_jobs do
748         post :lost_password, :params => { :user => { :email => third_user.email } }
749       end
750     end
751     assert_response :redirect
752     assert_redirected_to :action => :login
753     assert_match(/^Sorry you lost it/, flash[:notice])
754     email = ActionMailer::Base.deliveries.first
755     assert_equal 1, email.to.count
756     assert_equal third_user.email, email.to.first
757     ActionMailer::Base.deliveries.clear
758
759     # Test resetting using an address that matches a user that has the
760     # same (case insensitively unique) address in a different case
761     assert_difference "ActionMailer::Base.deliveries.size", 1 do
762       perform_enqueued_jobs do
763         post :lost_password, :params => { :user => { :email => third_user.email.upcase } }
764       end
765     end
766     assert_response :redirect
767     assert_redirected_to :action => :login
768     assert_match(/^Sorry you lost it/, flash[:notice])
769     email = ActionMailer::Base.deliveries.first
770     assert_equal 1, email.to.count
771     assert_equal third_user.email, email.to.first
772     ActionMailer::Base.deliveries.clear
773   end
774
775   def test_reset_password
776     user = create(:user, :pending)
777     # Test a request with no token
778     get :reset_password
779     assert_response :bad_request
780
781     # Test a request with a bogus token
782     get :reset_password, :params => { :token => "made_up_token" }
783     assert_response :redirect
784     assert_redirected_to :action => :lost_password
785
786     # Create a valid token for a user
787     token = user.tokens.create
788
789     # Test a request with a valid token
790     get :reset_password, :params => { :token => token.token }
791     assert_response :success
792     assert_template :reset_password
793
794     # Test that errors are reported for erroneous submissions
795     post :reset_password, :params => { :token => token.token, :user => { :pass_crypt => "new_password", :pass_crypt_confirmation => "different_password" } }
796     assert_response :success
797     assert_template :reset_password
798     assert_select "div#errorExplanation"
799
800     # Test setting a new password
801     post :reset_password, :params => { :token => token.token, :user => { :pass_crypt => "new_password", :pass_crypt_confirmation => "new_password" } }
802     assert_response :redirect
803     assert_redirected_to root_path
804     assert_equal user.id, session[:user]
805     user.reload
806     assert_equal "active", user.status
807     assert_equal true, user.email_valid
808     assert_equal user, User.authenticate(:username => user.email, :password => "new_password")
809   end
810
811   def test_account
812     # Get a user to work with - note that this user deliberately
813     # conflicts with uppercase_user in the email and display name
814     # fields to test that we can change other fields without any
815     # validation errors being reported
816     user = create(:user, :languages => [])
817     _uppercase_user = build(:user, :email => user.email.upcase, :display_name => user.display_name.upcase).tap { |u| u.save(:validate => false) }
818
819     # Make sure that you are redirected to the login page when
820     # you are not logged in
821     get :account, :params => { :display_name => user.display_name }
822     assert_response :redirect
823     assert_redirected_to :action => "login", :referer => "/user/#{ERB::Util.u(user.display_name)}/account"
824
825     # Make sure that you are blocked when not logged in as the right user
826     get :account, :params => { :display_name => user.display_name }, :session => { :user => create(:user) }
827     assert_response :forbidden
828
829     # Make sure we get the page when we are logged in as the right user
830     get :account, :params => { :display_name => user.display_name }, :session => { :user => user }
831     assert_response :success
832     assert_template :account
833     assert_select "form#accountForm" do |form|
834       assert_equal "post", form.attr("method").to_s
835       assert_select "input[name='_method']", false
836       assert_equal "/user/#{ERB::Util.u(user.display_name)}/account", form.attr("action").to_s
837     end
838
839     # Updating the description should work
840     user.description = "new description"
841     user.preferred_editor = "default"
842     post :account, :params => { :display_name => user.display_name, :user => user.attributes }, :session => { :user => user }
843     assert_response :success
844     assert_template :account
845     assert_select "div#errorExplanation", false
846     assert_select ".notice", /^User information updated successfully/
847     assert_select "form#accountForm > fieldset > div.form-row > div#user_description_container > div#user_description_content > textarea#user_description", user.description
848
849     # Changing to a invalid editor should fail
850     user.preferred_editor = "unknown"
851     post :account, :params => { :display_name => user.display_name, :user => user.attributes }, :session => { :user => user }
852     assert_response :success
853     assert_template :account
854     assert_select ".notice", false
855     assert_select "div#errorExplanation"
856     assert_select "form#accountForm > fieldset > div.form-row > select#user_preferred_editor > option[selected]", false
857
858     # Changing to a valid editor should work
859     user.preferred_editor = "potlatch2"
860     post :account, :params => { :display_name => user.display_name, :user => user.attributes }, :session => { :user => user }
861     assert_response :success
862     assert_template :account
863     assert_select "div#errorExplanation", false
864     assert_select ".notice", /^User information updated successfully/
865     assert_select "form#accountForm > fieldset > div.form-row > select#user_preferred_editor > option[selected][value=?]", "potlatch2"
866
867     # Changing to the default editor should work
868     user.preferred_editor = "default"
869     post :account, :params => { :display_name => user.display_name, :user => user.attributes }, :session => { :user => user }
870     assert_response :success
871     assert_template :account
872     assert_select "div#errorExplanation", false
873     assert_select ".notice", /^User information updated successfully/
874     assert_select "form#accountForm > fieldset > div.form-row > select#user_preferred_editor > option[selected]", false
875
876     # Changing to an uploaded image should work
877     image = Rack::Test::UploadedFile.new("test/gpx/fixtures/a.gif", "image/gif")
878     post :account, :params => { :display_name => user.display_name, :image_action => "new", :user => user.attributes.merge(:image => image) }, :session => { :user => user }
879     assert_response :success
880     assert_template :account
881     assert_select "div#errorExplanation", false
882     assert_select ".notice", /^User information updated successfully/
883     assert_select "form#accountForm > fieldset > div.form-row.accountImage input[name=image_action][checked][value=?]", "keep"
884
885     # Changing to a gravatar image should work
886     post :account, :params => { :display_name => user.display_name, :image_action => "gravatar", :user => user.attributes }, :session => { :user => user }
887     assert_response :success
888     assert_template :account
889     assert_select "div#errorExplanation", false
890     assert_select ".notice", /^User information updated successfully/
891     assert_select "form#accountForm > fieldset > div.form-row.accountImage input[name=image_action][checked][value=?]", "gravatar"
892
893     # Removing the image should work
894     post :account, :params => { :display_name => user.display_name, :image_action => "delete", :user => user.attributes }, :session => { :user => user }
895     assert_response :success
896     assert_template :account
897     assert_select "div#errorExplanation", false
898     assert_select ".notice", /^User information updated successfully/
899     assert_select "form#accountForm > fieldset > div.form-row.accountImage input[name=image_action][checked]", false
900
901     # Adding external authentication should redirect to the auth provider
902     post :account, :params => { :display_name => user.display_name, :user => user.attributes.merge(:auth_provider => "openid", :auth_uid => "gmail.com") }, :session => { :user => user }
903     assert_response :redirect
904     assert_redirected_to auth_path(:provider => "openid", :openid_url => "https://www.google.com/accounts/o8/id", :origin => "/user/#{ERB::Util.u(user.display_name)}/account")
905
906     # Changing name to one that exists should fail
907     new_attributes = user.attributes.dup.merge(:display_name => create(:user).display_name)
908     post :account, :params => { :display_name => user.display_name, :user => new_attributes }, :session => { :user => user }
909     assert_response :success
910     assert_template :account
911     assert_select ".notice", false
912     assert_select "div#errorExplanation"
913     assert_select "form#accountForm > fieldset > div.form-row > input.field_with_errors#user_display_name"
914
915     # Changing name to one that exists should fail, regardless of case
916     new_attributes = user.attributes.dup.merge(:display_name => create(:user).display_name.upcase)
917     post :account, :params => { :display_name => user.display_name, :user => new_attributes }, :session => { :user => user }
918     assert_response :success
919     assert_template :account
920     assert_select ".notice", false
921     assert_select "div#errorExplanation"
922     assert_select "form#accountForm > fieldset > div.form-row > input.field_with_errors#user_display_name"
923
924     # Changing name to one that doesn't exist should work
925     new_attributes = user.attributes.dup.merge(:display_name => "new tester")
926     post :account, :params => { :display_name => user.display_name, :user => new_attributes }, :session => { :user => user }
927     assert_response :success
928     assert_template :account
929     assert_select "div#errorExplanation", false
930     assert_select ".notice", /^User information updated successfully/
931     assert_select "form#accountForm > fieldset > div.form-row > input#user_display_name[value=?]", "new tester"
932
933     # Record the change of name
934     user.display_name = "new tester"
935
936     # Changing email to one that exists should fail
937     user.new_email = create(:user).email
938     assert_no_difference "ActionMailer::Base.deliveries.size" do
939       perform_enqueued_jobs do
940         post :account, :params => { :display_name => user.display_name, :user => user.attributes }, :session => { :user => user }
941       end
942     end
943     assert_response :success
944     assert_template :account
945     assert_select ".notice", false
946     assert_select "div#errorExplanation"
947     assert_select "form#accountForm > fieldset > div.form-row > input.field_with_errors#user_new_email"
948
949     # Changing email to one that exists should fail, regardless of case
950     user.new_email = create(:user).email.upcase
951     assert_no_difference "ActionMailer::Base.deliveries.size" do
952       perform_enqueued_jobs do
953         post :account, :params => { :display_name => user.display_name, :user => user.attributes }, :session => { :user => user }
954       end
955     end
956     assert_response :success
957     assert_template :account
958     assert_select ".notice", false
959     assert_select "div#errorExplanation"
960     assert_select "form#accountForm > fieldset > div.form-row > input.field_with_errors#user_new_email"
961
962     # Changing email to one that doesn't exist should work
963     user.new_email = "new_tester@example.com"
964     assert_difference "ActionMailer::Base.deliveries.size", 1 do
965       perform_enqueued_jobs do
966         post :account, :params => { :display_name => user.display_name, :user => user.attributes }, :session => { :user => user }
967       end
968     end
969     assert_response :success
970     assert_template :account
971     assert_select "div#errorExplanation", false
972     assert_select ".notice", /^User information updated successfully/
973     assert_select "form#accountForm > fieldset > div.form-row > input#user_new_email[value=?]", user.new_email
974     email = ActionMailer::Base.deliveries.first
975     assert_equal 1, email.to.count
976     assert_equal user.new_email, email.to.first
977     ActionMailer::Base.deliveries.clear
978   end
979
980   # Check that the user account page will display and contains some relevant
981   # information for the user
982   def test_show
983     # Test a non-existent user
984     get :show, :params => { :display_name => "unknown" }
985     assert_response :not_found
986
987     # Test a normal user
988     user = create(:user, :home_lon => 1.1, :home_lat => 1.1)
989     friend_user = create(:user, :home_lon => 1.2, :home_lat => 1.2)
990     create(:friend, :befriender => user, :befriendee => friend_user)
991     create(:changeset, :user => friend_user)
992
993     get :show, :params => { :display_name => user.display_name }
994     assert_response :success
995     assert_select "div#userinformation" do
996       assert_select "a[href^='/user/#{ERB::Util.u(user.display_name)}/history']", 1
997       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/traces']", 1
998       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/diary']", 1
999       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/diary/comments']", 1
1000       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/account']", 0
1001       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/blocks']", 0
1002       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/blocks_by']", 0
1003       assert_select "a[href='/blocks/new/#{ERB::Util.u(user.display_name)}']", 0
1004     end
1005
1006     # Friends shouldn't be visible as we're not logged in
1007     assert_select "div#friends-container", :count => 0
1008
1009     # Test a user who has been blocked
1010     blocked_user = create(:user)
1011     create(:user_block, :user => blocked_user)
1012     get :show, :params => { :display_name => blocked_user.display_name }
1013     assert_response :success
1014     assert_select "div#userinformation" do
1015       assert_select "a[href^='/user/#{ERB::Util.u(blocked_user.display_name)}/history']", 1
1016       assert_select "a[href='/user/#{ERB::Util.u(blocked_user.display_name)}/traces']", 1
1017       assert_select "a[href='/user/#{ERB::Util.u(blocked_user.display_name)}/diary']", 1
1018       assert_select "a[href='/user/#{ERB::Util.u(blocked_user.display_name)}/diary/comments']", 1
1019       assert_select "a[href='/user/#{ERB::Util.u(blocked_user.display_name)}/account']", 0
1020       assert_select "a[href='/user/#{ERB::Util.u(blocked_user.display_name)}/blocks']", 1
1021       assert_select "a[href='/user/#{ERB::Util.u(blocked_user.display_name)}/blocks_by']", 0
1022       assert_select "a[href='/blocks/new/#{ERB::Util.u(blocked_user.display_name)}']", 0
1023     end
1024
1025     # Test a moderator who has applied blocks
1026     moderator_user = create(:moderator_user)
1027     create(:user_block, :creator => moderator_user)
1028     get :show, :params => { :display_name => moderator_user.display_name }
1029     assert_response :success
1030     assert_select "div#userinformation" do
1031       assert_select "a[href^='/user/#{ERB::Util.u(moderator_user.display_name)}/history']", 1
1032       assert_select "a[href='/user/#{ERB::Util.u(moderator_user.display_name)}/traces']", 1
1033       assert_select "a[href='/user/#{ERB::Util.u(moderator_user.display_name)}/diary']", 1
1034       assert_select "a[href='/user/#{ERB::Util.u(moderator_user.display_name)}/diary/comments']", 1
1035       assert_select "a[href='/user/#{ERB::Util.u(moderator_user.display_name)}/account']", 0
1036       assert_select "a[href='/user/#{ERB::Util.u(moderator_user.display_name)}/blocks']", 0
1037       assert_select "a[href='/user/#{ERB::Util.u(moderator_user.display_name)}/blocks_by']", 1
1038       assert_select "a[href='/blocks/new/#{ERB::Util.u(moderator_user.display_name)}']", 0
1039     end
1040
1041     # Login as a normal user
1042     session[:user] = user.id
1043
1044     # Test the normal user
1045     get :show, :params => { :display_name => user.display_name }
1046     assert_response :success
1047     assert_select "div#userinformation" do
1048       assert_select "a[href^='/user/#{ERB::Util.u(user.display_name)}/history']", 1
1049       assert_select "a[href='/traces/mine']", 1
1050       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/diary']", 1
1051       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/diary/comments']", 1
1052       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/account']", 1
1053       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/blocks']", 0
1054       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/blocks_by']", 0
1055       assert_select "a[href='/blocks/new/#{ERB::Util.u(user.display_name)}']", 0
1056     end
1057
1058     # Friends should be visible as we're now logged in
1059     assert_select "div#friends-container" do
1060       assert_select "div.contact-activity", :count => 1
1061     end
1062
1063     # Login as a moderator
1064     session[:user] = create(:moderator_user).id
1065
1066     # Test the normal user
1067     get :show, :params => { :display_name => user.display_name }
1068     assert_response :success
1069     assert_select "div#userinformation" do
1070       assert_select "a[href^='/user/#{ERB::Util.u(user.display_name)}/history']", 1
1071       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/traces']", 1
1072       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/diary']", 1
1073       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/diary/comments']", 1
1074       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/account']", 0
1075       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/blocks']", 0
1076       assert_select "a[href='/user/#{ERB::Util.u(user.display_name)}/blocks_by']", 0
1077       assert_select "a[href='/blocks/new/#{ERB::Util.u(user.display_name)}']", 1
1078     end
1079   end
1080
1081   # Test whether information about contributor terms is shown for users who haven't agreed
1082   def test_terms_not_agreed
1083     agreed_user = create(:user, :terms_agreed => 3.days.ago)
1084     seen_user = create(:user, :terms_seen => true, :terms_agreed => nil)
1085     not_seen_user = create(:user, :terms_seen => false, :terms_agreed => nil)
1086
1087     get :show, :params => { :display_name => agreed_user.display_name }
1088     assert_response :success
1089     assert_select "div#userinformation" do
1090       assert_select "p", :count => 0, :text => /Contributor terms/
1091     end
1092
1093     get :show, :params => { :display_name => seen_user.display_name }
1094     assert_response :success
1095     # put @response.body
1096     assert_select "div#userinformation" do
1097       assert_select "p", :count => 1, :text => /Contributor terms/
1098       assert_select "p", /Declined/
1099     end
1100
1101     get :show, :params => { :display_name => not_seen_user.display_name }
1102     assert_response :success
1103     assert_select "div#userinformation" do
1104       assert_select "p", :count => 1, :text => /Contributor terms/
1105       assert_select "p", /Undecided/
1106     end
1107   end
1108
1109   def test_make_friend
1110     # Get users to work with
1111     user = create(:user)
1112     friend = create(:user)
1113
1114     # Check that the users aren't already friends
1115     assert_nil Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1116
1117     # When not logged in a GET should ask us to login
1118     get :make_friend, :params => { :display_name => friend.display_name }
1119     assert_redirected_to :action => "login", :referer => make_friend_path(:display_name => friend.display_name)
1120
1121     # When not logged in a POST should error
1122     post :make_friend, :params => { :display_name => friend.display_name }
1123     assert_response :forbidden
1124     assert_nil Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1125
1126     # When logged in a GET should get a confirmation page
1127     get :make_friend, :params => { :display_name => friend.display_name }, :session => { :user => user }
1128     assert_response :success
1129     assert_template :make_friend
1130     assert_select "form" do
1131       assert_select "input[type='hidden'][name='referer']", 0
1132       assert_select "input[type='submit']", 1
1133     end
1134     assert_nil Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1135
1136     # When logged in a POST should add the friendship
1137     assert_difference "ActionMailer::Base.deliveries.size", 1 do
1138       perform_enqueued_jobs do
1139         post :make_friend, :params => { :display_name => friend.display_name }, :session => { :user => user }
1140       end
1141     end
1142     assert_redirected_to user_path(friend)
1143     assert_match(/is now your friend/, flash[:notice])
1144     assert Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1145     email = ActionMailer::Base.deliveries.first
1146     assert_equal 1, email.to.count
1147     assert_equal friend.email, email.to.first
1148     ActionMailer::Base.deliveries.clear
1149
1150     # A second POST should report that the friendship already exists
1151     assert_no_difference "ActionMailer::Base.deliveries.size" do
1152       perform_enqueued_jobs do
1153         post :make_friend, :params => { :display_name => friend.display_name }, :session => { :user => user }
1154       end
1155     end
1156     assert_redirected_to user_path(friend)
1157     assert_match(/You are already friends with/, flash[:warning])
1158     assert Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1159   end
1160
1161   def test_make_friend_with_referer
1162     # Get users to work with
1163     user = create(:user)
1164     friend = create(:user)
1165
1166     # Check that the users aren't already friends
1167     assert_nil Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1168
1169     # The GET should preserve any referer
1170     get :make_friend, :params => { :display_name => friend.display_name, :referer => "/test" }, :session => { :user => user }
1171     assert_response :success
1172     assert_template :make_friend
1173     assert_select "form" do
1174       assert_select "input[type='hidden'][name='referer'][value='/test']", 1
1175       assert_select "input[type='submit']", 1
1176     end
1177     assert_nil Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1178
1179     # When logged in a POST should add the friendship and refer us
1180     assert_difference "ActionMailer::Base.deliveries.size", 1 do
1181       perform_enqueued_jobs do
1182         post :make_friend, :params => { :display_name => friend.display_name, :referer => "/test" }, :session => { :user => user }
1183       end
1184     end
1185     assert_redirected_to "/test"
1186     assert_match(/is now your friend/, flash[:notice])
1187     assert Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1188     email = ActionMailer::Base.deliveries.first
1189     assert_equal 1, email.to.count
1190     assert_equal friend.email, email.to.first
1191     ActionMailer::Base.deliveries.clear
1192   end
1193
1194   def test_make_friend_unkown_user
1195     # Should error when a bogus user is specified
1196     get :make_friend, :params => { :display_name => "No Such User" }, :session => { :user => create(:user) }
1197     assert_response :not_found
1198     assert_template :no_such_user
1199   end
1200
1201   def test_remove_friend
1202     # Get users to work with
1203     user = create(:user)
1204     friend = create(:user)
1205     create(:friend, :befriender => user, :befriendee => friend)
1206
1207     # Check that the users are friends
1208     assert Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1209
1210     # When not logged in a GET should ask us to login
1211     get :remove_friend, :params => { :display_name => friend.display_name }
1212     assert_redirected_to :action => "login", :referer => remove_friend_path(:display_name => friend.display_name)
1213
1214     # When not logged in a POST should error
1215     post :remove_friend, :params => { :display_name => friend.display_name }
1216     assert_response :forbidden
1217     assert Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1218
1219     # When logged in a GET should get a confirmation page
1220     get :remove_friend, :params => { :display_name => friend.display_name }, :session => { :user => user }
1221     assert_response :success
1222     assert_template :remove_friend
1223     assert_select "form" do
1224       assert_select "input[type='hidden'][name='referer']", 0
1225       assert_select "input[type='submit']", 1
1226     end
1227     assert Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1228
1229     # When logged in a POST should remove the friendship
1230     post :remove_friend, :params => { :display_name => friend.display_name }, :session => { :user => user }
1231     assert_redirected_to user_path(friend)
1232     assert_match(/was removed from your friends/, flash[:notice])
1233     assert_nil Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1234
1235     # A second POST should report that the friendship does not exist
1236     post :remove_friend, :params => { :display_name => friend.display_name }, :session => { :user => user }
1237     assert_redirected_to user_path(friend)
1238     assert_match(/is not one of your friends/, flash[:error])
1239     assert_nil Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1240   end
1241
1242   def test_remove_friend_with_referer
1243     # Get users to work with
1244     user = create(:user)
1245     friend = create(:user)
1246     create(:friend, :user_id => user.id, :friend_user_id => friend.id)
1247
1248     # Check that the users are friends
1249     assert Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1250
1251     # The GET should preserve any referer
1252     get :remove_friend, :params => { :display_name => friend.display_name, :referer => "/test" }, :session => { :user => user }
1253     assert_response :success
1254     assert_template :remove_friend
1255     assert_select "form" do
1256       assert_select "input[type='hidden'][name='referer'][value='/test']", 1
1257       assert_select "input[type='submit']", 1
1258     end
1259     assert Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1260
1261     # When logged in a POST should remove the friendship and refer
1262     post :remove_friend, :params => { :display_name => friend.display_name, :referer => "/test" }, :session => { :user => user }
1263     assert_redirected_to "/test"
1264     assert_match(/was removed from your friends/, flash[:notice])
1265     assert_nil Friend.where(:user_id => user.id, :friend_user_id => friend.id).first
1266   end
1267
1268   def test_remove_friend_unkown_user
1269     # Should error when a bogus user is specified
1270     get :remove_friend, :params => { :display_name => "No Such User" }, :session => { :user => create(:user) }
1271     assert_response :not_found
1272     assert_template :no_such_user
1273   end
1274
1275   def test_set_status
1276     user = create(:user)
1277
1278     # Try without logging in
1279     get :set_status, :params => { :display_name => user.display_name, :status => "suspended" }
1280     assert_response :redirect
1281     assert_redirected_to :action => :login, :referer => set_status_user_path(:status => "suspended")
1282
1283     # Now try as a normal user
1284     get :set_status, :params => { :display_name => user.display_name, :status => "suspended" }, :session => { :user => user }
1285     assert_response :redirect
1286     assert_redirected_to :controller => :errors, :action => :forbidden
1287
1288     # Finally try as an administrator
1289     get :set_status, :params => { :display_name => user.display_name, :status => "suspended" }, :session => { :user => create(:administrator_user) }
1290     assert_response :redirect
1291     assert_redirected_to :action => :show, :display_name => user.display_name
1292     assert_equal "suspended", User.find(user.id).status
1293   end
1294
1295   def test_delete
1296     user = create(:user, :home_lat => 12.1, :home_lon => 12.1, :description => "test")
1297
1298     # Try without logging in
1299     get :delete, :params => { :display_name => user.display_name, :status => "suspended" }
1300     assert_response :redirect
1301     assert_redirected_to :action => :login, :referer => delete_user_path(:status => "suspended")
1302
1303     # Now try as a normal user
1304     get :delete, :params => { :display_name => user.display_name, :status => "suspended" }, :session => { :user => user }
1305     assert_response :redirect
1306     assert_redirected_to :controller => :errors, :action => :forbidden
1307
1308     # Finally try as an administrator
1309     get :delete, :params => { :display_name => user.display_name, :status => "suspended" }, :session => { :user => create(:administrator_user) }
1310     assert_response :redirect
1311     assert_redirected_to :action => :show, :display_name => user.display_name
1312
1313     # Check that the user was deleted properly
1314     user.reload
1315     assert_equal "user_#{user.id}", user.display_name
1316     assert_equal "", user.description
1317     assert_nil user.home_lat
1318     assert_nil user.home_lon
1319     assert_equal false, user.image.file?
1320     assert_equal false, user.email_valid
1321     assert_nil user.new_email
1322     assert_nil user.auth_provider
1323     assert_nil user.auth_uid
1324     assert_equal "deleted", user.status
1325   end
1326
1327   def test_index_get
1328     user = create(:user)
1329     moderator_user = create(:moderator_user)
1330     administrator_user = create(:administrator_user)
1331     _suspended_user = create(:user, :suspended)
1332     _ip_user = create(:user, :creation_ip => "1.2.3.4")
1333
1334     # There are now 7 users - the five above, plus two extra "granters" for the
1335     # moderator_user and administrator_user
1336     assert_equal 7, User.count
1337
1338     # Shouldn't work when not logged in
1339     get :index
1340     assert_response :redirect
1341     assert_redirected_to :action => :login, :referer => users_path
1342
1343     session[:user] = user.id
1344
1345     # Shouldn't work when logged in as a normal user
1346     get :index
1347     assert_response :redirect
1348     assert_redirected_to :controller => :errors, :action => :forbidden
1349
1350     session[:user] = moderator_user.id
1351
1352     # Shouldn't work when logged in as a moderator
1353     get :index
1354     assert_response :redirect
1355     assert_redirected_to :controller => :errors, :action => :forbidden
1356
1357     session[:user] = administrator_user.id
1358
1359     # Note there is a header row, so all row counts are users + 1
1360     # Should work when logged in as an administrator
1361     get :index
1362     assert_response :success
1363     assert_template :index
1364     assert_select "table#user_list tr", :count => 7 + 1
1365
1366     # Should be able to limit by status
1367     get :index, :params => { :status => "suspended" }
1368     assert_response :success
1369     assert_template :index
1370     assert_select "table#user_list tr", :count => 1 + 1
1371
1372     # Should be able to limit by IP address
1373     get :index, :params => { :ip => "1.2.3.4" }
1374     assert_response :success
1375     assert_template :index
1376     assert_select "table#user_list tr", :count => 1 + 1
1377   end
1378
1379   def test_index_get_paginated
1380     1.upto(100).each do |n|
1381       User.create(:display_name => "extra_#{n}",
1382                   :email => "extra#{n}@example.com",
1383                   :pass_crypt => "extraextra")
1384     end
1385
1386     session[:user] = create(:administrator_user).id
1387
1388     # 100 examples, an administrator, and a granter for the admin.
1389     assert_equal 102, User.count
1390
1391     get :index
1392     assert_response :success
1393     assert_template :index
1394     assert_select "table#user_list tr", :count => 51
1395
1396     get :index, :params => { :page => 2 }
1397     assert_response :success
1398     assert_template :index
1399     assert_select "table#user_list tr", :count => 51
1400
1401     get :index, :params => { :page => 3 }
1402     assert_response :success
1403     assert_template :index
1404     assert_select "table#user_list tr", :count => 3
1405   end
1406
1407   def test_index_post_confirm
1408     inactive_user = create(:user, :pending)
1409     suspended_user = create(:user, :suspended)
1410
1411     # Shouldn't work when not logged in
1412     assert_no_difference "User.active.count" do
1413       post :index, :params => { :confirm => 1, :user => { inactive_user.id => 1, suspended_user.id => 1 } }
1414     end
1415     assert_response :forbidden
1416
1417     assert_equal "pending", inactive_user.reload.status
1418     assert_equal "suspended", suspended_user.reload.status
1419
1420     session[:user] = create(:user).id
1421
1422     # Shouldn't work when logged in as a normal user
1423     assert_no_difference "User.active.count" do
1424       post :index, :params => { :confirm => 1, :user => { inactive_user.id => 1, suspended_user.id => 1 } }
1425     end
1426     assert_response :redirect
1427     assert_redirected_to :controller => :errors, :action => :forbidden
1428     assert_equal "pending", inactive_user.reload.status
1429     assert_equal "suspended", suspended_user.reload.status
1430
1431     session[:user] = create(:moderator_user).id
1432
1433     # Shouldn't work when logged in as a moderator
1434     assert_no_difference "User.active.count" do
1435       post :index, :params => { :confirm => 1, :user => { inactive_user.id => 1, suspended_user.id => 1 } }
1436     end
1437     assert_response :redirect
1438     assert_redirected_to :controller => :errors, :action => :forbidden
1439     assert_equal "pending", inactive_user.reload.status
1440     assert_equal "suspended", suspended_user.reload.status
1441
1442     session[:user] = create(:administrator_user).id
1443
1444     # Should work when logged in as an administrator
1445     assert_difference "User.active.count", 2 do
1446       post :index, :params => { :confirm => 1, :user => { inactive_user.id => 1, suspended_user.id => 1 } }
1447     end
1448     assert_response :redirect
1449     assert_redirected_to :action => :index
1450     assert_equal "confirmed", inactive_user.reload.status
1451     assert_equal "confirmed", suspended_user.reload.status
1452   end
1453
1454   def test_index_post_hide
1455     normal_user = create(:user)
1456     confirmed_user = create(:user, :confirmed)
1457
1458     # Shouldn't work when not logged in
1459     assert_no_difference "User.active.count" do
1460       post :index, :params => { :hide => 1, :user => { normal_user.id => 1, confirmed_user.id => 1 } }
1461     end
1462     assert_response :forbidden
1463
1464     assert_equal "active", normal_user.reload.status
1465     assert_equal "confirmed", confirmed_user.reload.status
1466
1467     session[:user] = create(:user).id
1468
1469     # Shouldn't work when logged in as a normal user
1470     assert_no_difference "User.active.count" do
1471       post :index, :params => { :hide => 1, :user => { normal_user.id => 1, confirmed_user.id => 1 } }
1472     end
1473     assert_response :redirect
1474     assert_redirected_to :controller => :errors, :action => :forbidden
1475     assert_equal "active", normal_user.reload.status
1476     assert_equal "confirmed", confirmed_user.reload.status
1477
1478     session[:user] = create(:moderator_user).id
1479
1480     # Shouldn't work when logged in as a moderator
1481     assert_no_difference "User.active.count" do
1482       post :index, :params => { :hide => 1, :user => { normal_user.id => 1, confirmed_user.id => 1 } }
1483     end
1484     assert_response :redirect
1485     assert_redirected_to :controller => :errors, :action => :forbidden
1486     assert_equal "active", normal_user.reload.status
1487     assert_equal "confirmed", confirmed_user.reload.status
1488
1489     session[:user] = create(:administrator_user).id
1490
1491     # Should work when logged in as an administrator
1492     assert_difference "User.active.count", -2 do
1493       post :index, :params => { :hide => 1, :user => { normal_user.id => 1, confirmed_user.id => 1 } }
1494     end
1495     assert_response :redirect
1496     assert_redirected_to :action => :index
1497     assert_equal "deleted", normal_user.reload.status
1498     assert_equal "deleted", confirmed_user.reload.status
1499   end
1500 end