devise 3.4.1 → 3.5.10

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of devise might be problematic. Click here for more details.

Files changed (116) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +28 -19
  3. data/CHANGELOG.md +193 -104
  4. data/CODE_OF_CONDUCT.md +22 -0
  5. data/CONTRIBUTING.md +2 -0
  6. data/Gemfile +3 -2
  7. data/Gemfile.lock +90 -95
  8. data/MIT-LICENSE +1 -1
  9. data/README.md +55 -34
  10. data/Rakefile +2 -1
  11. data/app/controllers/devise/confirmations_controller.rb +4 -0
  12. data/app/controllers/devise/omniauth_callbacks_controller.rb +4 -0
  13. data/app/controllers/devise/passwords_controller.rb +14 -4
  14. data/app/controllers/devise/registrations_controller.rb +10 -11
  15. data/app/controllers/devise/sessions_controller.rb +7 -2
  16. data/app/controllers/devise/unlocks_controller.rb +3 -0
  17. data/app/controllers/devise_controller.rb +34 -18
  18. data/app/mailers/devise/mailer.rb +4 -0
  19. data/app/views/devise/confirmations/new.html.erb +1 -1
  20. data/app/views/devise/mailer/password_change.html.erb +3 -0
  21. data/app/views/devise/passwords/edit.html.erb +3 -0
  22. data/app/views/devise/registrations/new.html.erb +1 -1
  23. data/app/views/devise/shared/_links.html.erb +1 -1
  24. data/config/locales/en.yml +2 -0
  25. data/devise.gemspec +0 -2
  26. data/gemfiles/Gemfile.rails-3.2-stable.lock +52 -49
  27. data/gemfiles/Gemfile.rails-4.0-stable +1 -0
  28. data/gemfiles/Gemfile.rails-4.0-stable.lock +61 -60
  29. data/gemfiles/Gemfile.rails-4.1-stable +1 -0
  30. data/gemfiles/Gemfile.rails-4.1-stable.lock +66 -65
  31. data/gemfiles/Gemfile.rails-4.2-stable +30 -0
  32. data/gemfiles/Gemfile.rails-4.2-stable.lock +193 -0
  33. data/lib/devise/controllers/helpers.rb +12 -6
  34. data/lib/devise/controllers/rememberable.rb +9 -2
  35. data/lib/devise/controllers/sign_in_out.rb +2 -8
  36. data/lib/devise/controllers/store_location.rb +3 -1
  37. data/lib/devise/controllers/url_helpers.rb +7 -9
  38. data/lib/devise/encryptor.rb +22 -0
  39. data/lib/devise/failure_app.rb +48 -13
  40. data/lib/devise/hooks/timeoutable.rb +5 -7
  41. data/lib/devise/mapping.rb +1 -0
  42. data/lib/devise/models/authenticatable.rb +20 -26
  43. data/lib/devise/models/confirmable.rb +51 -17
  44. data/lib/devise/models/database_authenticatable.rb +17 -11
  45. data/lib/devise/models/lockable.rb +5 -1
  46. data/lib/devise/models/recoverable.rb +23 -15
  47. data/lib/devise/models/rememberable.rb +56 -22
  48. data/lib/devise/models/timeoutable.rb +0 -6
  49. data/lib/devise/models/trackable.rb +1 -2
  50. data/lib/devise/models/validatable.rb +3 -3
  51. data/lib/devise/models.rb +1 -1
  52. data/lib/devise/rails/routes.rb +27 -18
  53. data/lib/devise/rails.rb +1 -1
  54. data/lib/devise/strategies/authenticatable.rb +7 -4
  55. data/lib/devise/strategies/database_authenticatable.rb +1 -1
  56. data/lib/devise/strategies/rememberable.rb +13 -6
  57. data/lib/devise/test_helpers.rb +2 -2
  58. data/lib/devise/version.rb +1 -1
  59. data/lib/devise.rb +37 -36
  60. data/lib/generators/active_record/templates/migration.rb +1 -1
  61. data/lib/generators/active_record/templates/migration_existing.rb +1 -1
  62. data/lib/generators/devise/views_generator.rb +14 -3
  63. data/lib/generators/templates/controllers/README +2 -2
  64. data/lib/generators/templates/controllers/omniauth_callbacks_controller.rb +1 -1
  65. data/lib/generators/templates/controllers/registrations_controller.rb +2 -2
  66. data/lib/generators/templates/controllers/sessions_controller.rb +1 -1
  67. data/lib/generators/templates/devise.rb +17 -11
  68. data/lib/generators/templates/markerb/confirmation_instructions.markerb +1 -1
  69. data/lib/generators/templates/markerb/password_change.markerb +3 -0
  70. data/lib/generators/templates/markerb/reset_password_instructions.markerb +1 -1
  71. data/lib/generators/templates/markerb/unlock_instructions.markerb +1 -1
  72. data/lib/generators/templates/simple_form_for/passwords/edit.html.erb +1 -1
  73. data/lib/generators/templates/simple_form_for/registrations/new.html.erb +1 -1
  74. data/test/controllers/custom_registrations_controller_test.rb +6 -1
  75. data/test/controllers/helper_methods_test.rb +21 -0
  76. data/test/controllers/helpers_test.rb +5 -0
  77. data/test/controllers/inherited_controller_i18n_messages_test.rb +51 -0
  78. data/test/controllers/internal_helpers_test.rb +4 -4
  79. data/test/controllers/load_hooks_controller_test.rb +19 -0
  80. data/test/controllers/passwords_controller_test.rb +1 -1
  81. data/test/controllers/sessions_controller_test.rb +3 -3
  82. data/test/devise_test.rb +3 -3
  83. data/test/failure_app_test.rb +40 -0
  84. data/test/generators/views_generator_test.rb +7 -0
  85. data/test/integration/database_authenticatable_test.rb +11 -0
  86. data/test/integration/omniauthable_test.rb +12 -10
  87. data/test/integration/recoverable_test.rb +13 -0
  88. data/test/integration/rememberable_test.rb +50 -3
  89. data/test/integration/timeoutable_test.rb +13 -18
  90. data/test/mailers/confirmation_instructions_test.rb +1 -1
  91. data/test/mapping_test.rb +6 -0
  92. data/test/models/confirmable_test.rb +93 -37
  93. data/test/models/database_authenticatable_test.rb +20 -0
  94. data/test/models/lockable_test.rb +29 -7
  95. data/test/models/recoverable_test.rb +62 -7
  96. data/test/models/rememberable_test.rb +68 -97
  97. data/test/models/validatable_test.rb +5 -5
  98. data/test/models_test.rb +15 -6
  99. data/test/rails_app/app/active_record/user_without_email.rb +8 -0
  100. data/test/rails_app/app/controllers/admins_controller.rb +0 -5
  101. data/test/rails_app/app/controllers/custom/registrations_controller.rb +10 -0
  102. data/test/rails_app/app/mongoid/user_without_email.rb +33 -0
  103. data/test/rails_app/config/application.rb +1 -1
  104. data/test/rails_app/config/environments/production.rb +6 -2
  105. data/test/rails_app/config/environments/test.rb +7 -2
  106. data/test/rails_app/config/initializers/devise.rb +12 -15
  107. data/test/rails_app/config/routes.rb +6 -3
  108. data/test/rails_app/lib/shared_user.rb +1 -1
  109. data/test/rails_app/lib/shared_user_without_email.rb +26 -0
  110. data/test/rails_test.rb +9 -0
  111. data/test/support/helpers.rb +4 -0
  112. data/test/support/integration.rb +2 -2
  113. data/test/test_helpers_test.rb +22 -7
  114. data/test/test_models.rb +2 -2
  115. data/test/time_helpers.rb +137 -0
  116. metadata +26 -4
@@ -8,7 +8,7 @@ class AddDeviseTo<%= table_name.camelize %> < ActiveRecord::Migration
8
8
  <% end -%>
9
9
 
10
10
  # Uncomment below if timestamps were not included in your original model.
11
- # t.timestamps
11
+ # t.timestamps null: false
12
12
  end
13
13
 
14
14
  add_index :<%= table_name %>, :email, unique: true
@@ -47,7 +47,7 @@ module Devise
47
47
  def view_directory(name, _target_path = nil)
48
48
  directory name.to_s, _target_path || "#{target_path}/#{name}" do |content|
49
49
  if scope
50
- content.gsub "devise/shared/links", "#{scope}/shared/links"
50
+ content.gsub "devise/shared/links", "#{plural_scope}/shared/links"
51
51
  else
52
52
  content
53
53
  end
@@ -55,7 +55,11 @@ module Devise
55
55
  end
56
56
 
57
57
  def target_path
58
- @target_path ||= "app/views/#{scope || :devise}"
58
+ @target_path ||= "app/views/#{plural_scope || :devise}"
59
+ end
60
+
61
+ def plural_scope
62
+ @plural_scope ||= scope.presence && scope.underscore.pluralize
59
63
  end
60
64
  end
61
65
 
@@ -83,6 +87,13 @@ module Devise
83
87
  source_root File.expand_path("../../templates/simple_form_for", __FILE__)
84
88
  desc "Copies simple form enabled views to your application."
85
89
  hide!
90
+
91
+ def copy_views
92
+ if options[:views]
93
+ options[:views].delete('mailer')
94
+ end
95
+ super
96
+ end
86
97
  end
87
98
 
88
99
  class ErbGenerator < Rails::Generators::Base #:nodoc:
@@ -111,7 +122,7 @@ module Devise
111
122
  end
112
123
 
113
124
  def target_path
114
- "app/views/#{scope || :devise}/mailer"
125
+ "app/views/#{plural_scope || :devise}/mailer"
115
126
  end
116
127
  end
117
128
 
@@ -2,12 +2,12 @@
2
2
 
3
3
  Some setup you must do manually if you haven't yet:
4
4
 
5
- Ensure you have overridden routes for generated controllers in your route.rb.
5
+ Ensure you have overridden routes for generated controllers in your routes.rb.
6
6
  For example:
7
7
 
8
8
  Rails.application.routes.draw do
9
9
  devise_for :users, controllers: {
10
- sessions: 'sessions'
10
+ sessions: 'users/sessions'
11
11
  }
12
12
  end
13
13
 
@@ -21,7 +21,7 @@ class <%= @scope_prefix %>OmniauthCallbacksController < Devise::OmniauthCallback
21
21
 
22
22
  # protected
23
23
 
24
- # The path used when omniauth fails
24
+ # The path used when OmniAuth fails
25
25
  # def after_omniauth_failure_path_for(scope)
26
26
  # super(scope)
27
27
  # end
@@ -38,12 +38,12 @@ class <%= @scope_prefix %>RegistrationsController < Devise::RegistrationsControl
38
38
 
39
39
  # protected
40
40
 
41
- # You can put the params you want to permit in the empty array.
41
+ # If you have extra params to permit, append them to the sanitizer.
42
42
  # def configure_sign_up_params
43
43
  # devise_parameter_sanitizer.for(:sign_up) << :attribute
44
44
  # end
45
45
 
46
- # You can put the params you want to permit in the empty array.
46
+ # If you have extra params to permit, append them to the sanitizer.
47
47
  # def configure_account_update_params
48
48
  # devise_parameter_sanitizer.for(:account_update) << :attribute
49
49
  # end
@@ -18,7 +18,7 @@ class <%= @scope_prefix %>SessionsController < Devise::SessionsController
18
18
 
19
19
  # protected
20
20
 
21
- # You can put the params you want to permit in the empty array.
21
+ # If you have extra params to permit, append them to the sanitizer.
22
22
  # def configure_sign_in_params
23
23
  # devise_parameter_sanitizer.for(:sign_in) << :attribute
24
24
  # end
@@ -4,6 +4,8 @@ Devise.setup do |config|
4
4
  # The secret key used by Devise. Devise uses this key to generate
5
5
  # random tokens. Changing this key will render invalid all existing
6
6
  # confirmation, reset password and unlock tokens in the database.
7
+ # Devise will use the `secret_key_base` on Rails 4+ applications as its `secret_key`
8
+ # by default. You can change it below and use your own secret key.
7
9
  <% if rails_4? -%>
8
10
  # config.secret_key = '<%= SecureRandom.hex(64) %>'
9
11
  <% else -%>
@@ -33,7 +35,7 @@ Devise.setup do |config|
33
35
  # session. If you need permissions, you should implement that in a before filter.
34
36
  # You can also supply a hash where the value is a boolean determining whether
35
37
  # or not authentication should be aborted when the value is not present.
36
- # config.authentication_keys = [ :email ]
38
+ # config.authentication_keys = [:email]
37
39
 
38
40
  # Configure parameters from the request object used for authentication. Each entry
39
41
  # given should be a request method and it will automatically be passed to the
@@ -45,12 +47,12 @@ Devise.setup do |config|
45
47
  # Configure which authentication keys should be case-insensitive.
46
48
  # These keys will be downcased upon creating or modifying a user and when used
47
49
  # to authenticate or find a user. Default is :email.
48
- config.case_insensitive_keys = [ :email ]
50
+ config.case_insensitive_keys = [:email]
49
51
 
50
52
  # Configure which authentication keys should have whitespace stripped.
51
53
  # These keys will have whitespace before and after removed upon creating or
52
54
  # modifying a user and when used to authenticate or find a user. Default is :email.
53
- config.strip_whitespace_keys = [ :email ]
55
+ config.strip_whitespace_keys = [:email]
54
56
 
55
57
  # Tell if authentication through request.params is enabled. True by default.
56
58
  # It can be set to an array that will enable params authentication only for the
@@ -103,6 +105,9 @@ Devise.setup do |config|
103
105
  # Setup a pepper to generate the encrypted password.
104
106
  # config.pepper = '<%= SecureRandom.hex(64) %>'
105
107
 
108
+ # Send a notification email when the user's password is changed
109
+ # config.send_password_change_notification = false
110
+
106
111
  # ==> Configuration for :confirmable
107
112
  # A period that the user is allowed to access the website even without
108
113
  # confirming their account. For instance, if set to 2.days, the user will be
@@ -126,7 +131,7 @@ Devise.setup do |config|
126
131
  config.reconfirmable = true
127
132
 
128
133
  # Defines which key will be used when confirming an account
129
- # config.confirmation_keys = [ :email ]
134
+ # config.confirmation_keys = [:email]
130
135
 
131
136
  # ==> Configuration for :rememberable
132
137
  # The time the user will be remembered without asking for credentials again.
@@ -144,7 +149,7 @@ Devise.setup do |config|
144
149
 
145
150
  # ==> Configuration for :validatable
146
151
  # Range for password length.
147
- config.password_length = 8..128
152
+ config.password_length = 8..72
148
153
 
149
154
  # Email regex used to validate email formats. It simply asserts that
150
155
  # one (and only one) @ exists in the given string. This is mainly
@@ -156,9 +161,6 @@ Devise.setup do |config|
156
161
  # time the user will be asked for credentials again. Default is 30 minutes.
157
162
  # config.timeout_in = 30.minutes
158
163
 
159
- # If true, expires auth token on session timeout.
160
- # config.expire_auth_token_on_timeout = false
161
-
162
164
  # ==> Configuration for :lockable
163
165
  # Defines which strategy will be used to lock an account.
164
166
  # :failed_attempts = Locks an account after a number of failed attempts to sign in.
@@ -166,7 +168,7 @@ Devise.setup do |config|
166
168
  # config.lock_strategy = :failed_attempts
167
169
 
168
170
  # Defines which key will be used when locking and unlocking an account
169
- # config.unlock_keys = [ :email ]
171
+ # config.unlock_keys = [:email]
170
172
 
171
173
  # Defines which strategy will be used to unlock an account.
172
174
  # :email = Sends an unlock link to the user email
@@ -188,13 +190,17 @@ Devise.setup do |config|
188
190
  # ==> Configuration for :recoverable
189
191
  #
190
192
  # Defines which key will be used when recovering the password for an account
191
- # config.reset_password_keys = [ :email ]
193
+ # config.reset_password_keys = [:email]
192
194
 
193
195
  # Time interval you can reset your password with a reset password key.
194
196
  # Don't put a too small interval or your users won't have the time to
195
197
  # change their passwords.
196
198
  config.reset_password_within = 6.hours
197
199
 
200
+ # When set to false, does not sign a user in automatically after their password is
201
+ # reset. Defaults to true, so a user is signed in automatically after a reset.
202
+ # config.sign_in_after_reset_password = true
203
+
198
204
  # ==> Configuration for :encryptable
199
205
  # Allow you to use another encryption algorithm besides bcrypt (default). You can use
200
206
  # :sha1, :sha512 or encryptors from others authentication tools as :clearance_sha1,
@@ -257,7 +263,7 @@ Devise.setup do |config|
257
263
  # The router that invoked `devise_for`, in the example above, would be:
258
264
  # config.router_name = :my_engine
259
265
  #
260
- # When using omniauth, Devise cannot automatically set Omniauth path,
266
+ # When using OmniAuth, Devise cannot automatically set OmniAuth path,
261
267
  # so you need to do it manually. For the users scope, it would be:
262
268
  # config.omniauth_path_prefix = '/my_engine/users/auth'
263
269
  end
@@ -2,4 +2,4 @@ Welcome <%= @email %>!
2
2
 
3
3
  You can confirm your account through the link below:
4
4
 
5
- <%= link_to 'Confirm my account', confirmation_url(@resource, confirmation_token: @token) %>
5
+ [Confirm my account](<%= confirmation_url(@resource, confirmation_token: @token) %>)
@@ -0,0 +1,3 @@
1
+ <p>Hello <%= @resource.email %>!</p>
2
+
3
+ <p>We're contacting you to notify you that your password has been changed.</p>
@@ -2,7 +2,7 @@ Hello <%= @resource.email %>!
2
2
 
3
3
  Someone has requested a link to change your password, and you can do this through the link below.
4
4
 
5
- <%= link_to 'Change my password', edit_password_url(@resource, reset_password_token: @token) %>
5
+ [Change my password](<%= edit_password_url(@resource, reset_password_token: @token) %>)
6
6
 
7
7
  If you didn't request this, please ignore this email.
8
8
  Your password won't change until you access the link above and create a new one.
@@ -4,4 +4,4 @@ Your account has been locked due to an excessive number of unsuccessful sign in
4
4
 
5
5
  Click the link below to unlock your account:
6
6
 
7
- <%= link_to 'Unlock my account', unlock_url(@resource, unlock_token: @token) %>
7
+ [Unlock my account](<%= unlock_url(@resource, unlock_token: @token) %>)
@@ -7,7 +7,7 @@
7
7
  <%= f.full_error :reset_password_token %>
8
8
 
9
9
  <div class="form-inputs">
10
- <%= f.input :password, label: "New password", required: true, autofocus: true %>
10
+ <%= f.input :password, label: "New password", required: true, autofocus: true, hint: ("#{@minimum_password_length} characters minimum" if @minimum_password_length) %>
11
11
  <%= f.input :password_confirmation, label: "Confirm your new password", required: true %>
12
12
  </div>
13
13
 
@@ -5,7 +5,7 @@
5
5
 
6
6
  <div class="form-inputs">
7
7
  <%= f.input :email, required: true, autofocus: true %>
8
- <%= f.input :password, required: true, hint: ("#{@minimum_password_length} characters minimum" if @validatable) %>
8
+ <%= f.input :password, required: true, hint: ("#{@minimum_password_length} characters minimum" if @minimum_password_length) %>
9
9
  <%= f.input :password_confirmation, required: true %>
10
10
  </div>
11
11
 
@@ -8,7 +8,7 @@ class CustomRegistrationsControllerTest < ActionController::TestCase
8
8
  setup do
9
9
  request.env["devise.mapping"] = Devise.mappings[:user]
10
10
  @password = 'password'
11
- @user = create_user(password: @password, password_confirmation: @password).tap(&:confirm!)
11
+ @user = create_user(password: @password, password_confirmation: @password).tap(&:confirm)
12
12
  end
13
13
 
14
14
  test "yield resource to block on create success" do
@@ -32,4 +32,9 @@ class CustomRegistrationsControllerTest < ActionController::TestCase
32
32
  put :update, { user: { } }
33
33
  assert @controller.update_block_called?, "update failed to yield resource to provided block"
34
34
  end
35
+
36
+ test "yield resource to block on new" do
37
+ get :new
38
+ assert @controller.new_block_called?, "new failed to yield resource to provided block"
39
+ end
35
40
  end
@@ -0,0 +1,21 @@
1
+ require 'test_helper'
2
+
3
+ class ApiController < ActionController::Metal
4
+ include Devise::Controllers::Helpers
5
+ end
6
+
7
+ class HelperMethodsTest < ActionController::TestCase
8
+ tests ApiController
9
+
10
+ test 'includes Devise::Controllers::Helpers' do
11
+ assert_includes @controller.class.ancestors, Devise::Controllers::Helpers
12
+ end
13
+
14
+ test 'does not respond_to helper_method' do
15
+ refute_respond_to @controller.class, :helper_method
16
+ end
17
+
18
+ test 'defines methods like current_user' do
19
+ assert_respond_to @controller, :current_user
20
+ end
21
+ end
@@ -245,6 +245,11 @@ class ControllerAuthenticatableTest < ActionController::TestCase
245
245
  assert_equal "/foo?bar=baz", @controller.stored_location_for(:user)
246
246
  end
247
247
 
248
+ test 'store location for stores fragments' do
249
+ @controller.store_location_for(:user, "/foo#bar")
250
+ assert_equal "/foo#bar", @controller.stored_location_for(:user)
251
+ end
252
+
248
253
  test 'after sign in path defaults to root path if none by was specified for the given scope' do
249
254
  assert_equal root_path, @controller.after_sign_in_path_for(:user)
250
255
  end
@@ -0,0 +1,51 @@
1
+ require 'test_helper'
2
+
3
+ class SessionsInheritedController < Devise::SessionsController
4
+ def test_i18n_scope
5
+ set_flash_message(:notice, :signed_in)
6
+ end
7
+ end
8
+
9
+ class AnotherInheritedController < SessionsInheritedController
10
+ protected
11
+
12
+ def translation_scope
13
+ 'another'
14
+ end
15
+ end
16
+
17
+ class InheritedControllerTest < ActionController::TestCase
18
+ tests SessionsInheritedController
19
+
20
+ def setup
21
+ @mock_warden = OpenStruct.new
22
+ @controller.request.env['warden'] = @mock_warden
23
+ @controller.request.env['devise.mapping'] = Devise.mappings[:user]
24
+ end
25
+
26
+ test 'I18n scope is inherited from Devise::Sessions' do
27
+ I18n.expects(:t).with do |message, options|
28
+ message == 'user.signed_in' &&
29
+ options[:scope] == 'devise.sessions'
30
+ end
31
+ @controller.test_i18n_scope
32
+ end
33
+ end
34
+
35
+ class AnotherInheritedControllerTest < ActionController::TestCase
36
+ tests AnotherInheritedController
37
+
38
+ def setup
39
+ @mock_warden = OpenStruct.new
40
+ @controller.request.env['warden'] = @mock_warden
41
+ @controller.request.env['devise.mapping'] = Devise.mappings[:user]
42
+ end
43
+
44
+ test 'I18n scope is overridden' do
45
+ I18n.expects(:t).with do |message, options|
46
+ message == 'user.signed_in' &&
47
+ options[:scope] == 'another'
48
+ end
49
+ @controller.test_i18n_scope
50
+ end
51
+ end
@@ -13,16 +13,16 @@ class HelpersTest < ActionController::TestCase
13
13
  end
14
14
 
15
15
  test 'get resource name from env' do
16
- assert_equal :user, @controller.resource_name
16
+ assert_equal :user, @controller.send(:resource_name)
17
17
  end
18
18
 
19
19
  test 'get resource class from env' do
20
- assert_equal User, @controller.resource_class
20
+ assert_equal User, @controller.send(:resource_class)
21
21
  end
22
22
 
23
23
  test 'get resource instance variable from env' do
24
24
  @controller.instance_variable_set(:@user, user = User.new)
25
- assert_equal user, @controller.resource
25
+ assert_equal user, @controller.send(:resource)
26
26
  end
27
27
 
28
28
  test 'set resource instance variable from env' do
@@ -80,7 +80,7 @@ class HelpersTest < ActionController::TestCase
80
80
 
81
81
  test 'signed in resource returns signed in resource for current scope' do
82
82
  @mock_warden.expects(:authenticate).with(scope: :user).returns(User.new)
83
- assert_kind_of User, @controller.signed_in_resource
83
+ assert_kind_of User, @controller.send(:signed_in_resource)
84
84
  end
85
85
 
86
86
  test 'is a devise controller' do
@@ -0,0 +1,19 @@
1
+ require 'test_helper'
2
+
3
+ class LoadHooksControllerTest < ActionController::TestCase
4
+ setup do
5
+ ActiveSupport.on_load(:devise_controller) do
6
+ define_method :defined_by_load_hook do
7
+ puts 'I am defined dynamically by activesupport load hook'
8
+ end
9
+ end
10
+ end
11
+
12
+ teardown do
13
+ DeviseController.class_eval { undef :defined_by_load_hook }
14
+ end
15
+
16
+ test 'load hook called when controller is loaded' do
17
+ assert DeviseController.instance_methods.include? :defined_by_load_hook
18
+ end
19
+ end
@@ -6,7 +6,7 @@ class PasswordsControllerTest < ActionController::TestCase
6
6
 
7
7
  setup do
8
8
  request.env["devise.mapping"] = Devise.mappings[:user]
9
- @user = create_user.tap(&:confirm!)
9
+ @user = create_user.tap(&:confirm)
10
10
  @raw = @user.send_reset_password_instructions
11
11
  end
12
12
 
@@ -36,7 +36,7 @@ class SessionsControllerTest < ActionController::TestCase
36
36
  request.session["user_return_to"] = 'foo.bar'
37
37
 
38
38
  user = create_user
39
- user.confirm!
39
+ user.confirm
40
40
  post :create, user: {
41
41
  email: user.email,
42
42
  password: user.password
@@ -50,7 +50,7 @@ class SessionsControllerTest < ActionController::TestCase
50
50
  request.session["user_return_to"] = 'foo.bar'
51
51
 
52
52
  user = create_user
53
- user.confirm!
53
+ user.confirm
54
54
  post :create, format: 'json', user: {
55
55
  email: user.email,
56
56
  password: user.password
@@ -72,7 +72,7 @@ class SessionsControllerTest < ActionController::TestCase
72
72
  test "#destroy doesn't set the flash if the requested format is not navigational" do
73
73
  request.env["devise.mapping"] = Devise.mappings[:user]
74
74
  user = create_user
75
- user.confirm!
75
+ user.confirm
76
76
  post :create, format: 'json', user: {
77
77
  email: user.email,
78
78
  password: user.password
data/test/devise_test.rb CHANGED
@@ -14,11 +14,11 @@ class DeviseTest < ActiveSupport::TestCase
14
14
  test 'bcrypt on the class' do
15
15
  password = "super secret"
16
16
  klass = Struct.new(:pepper, :stretches).new("blahblah", 2)
17
- hash = Devise.bcrypt(klass, password)
17
+ hash = Devise::Encryptor.digest(klass, password)
18
18
  assert_equal ::BCrypt::Password.create(hash), hash
19
19
 
20
20
  klass = Struct.new(:pepper, :stretches).new("bla", 2)
21
- hash = Devise.bcrypt(klass, password)
21
+ hash = Devise::Encryptor.digest(klass, password)
22
22
  assert_not_equal ::BCrypt::Password.new(hash), hash
23
23
  end
24
24
 
@@ -95,7 +95,7 @@ class DeviseTest < ActiveSupport::TestCase
95
95
 
96
96
  test 'Devise.email_regexp should match valid email addresses' do
97
97
  valid_emails = ["test@example.com", "jo@jo.co", "f4$_m@you.com", "testing.example@example.com.ua"]
98
- non_valid_emails = ["rex", "test@go,com", "test user@example.com", "test_user@example server.com"]
98
+ non_valid_emails = ["rex", "test@go,com", "test user@example.com", "test_user@example server.com", "test_user@example.com."]
99
99
 
100
100
  valid_emails.each do |email|
101
101
  assert_match Devise.email_regexp, email
@@ -26,6 +26,22 @@ class FailureTest < ActiveSupport::TestCase
26
26
  end
27
27
  end
28
28
 
29
+ class FakeEngineApp < Devise::FailureApp
30
+ class FakeEngine
31
+ def new_user_on_engine_session_url _
32
+ '/user_on_engines/sign_in'
33
+ end
34
+ end
35
+
36
+ def main_app
37
+ raise 'main_app router called instead of fake_engine'
38
+ end
39
+
40
+ def fake_engine
41
+ @fake_engine ||= FakeEngine.new
42
+ end
43
+ end
44
+
29
45
  def self.context(name, &block)
30
46
  instance_eval(&block)
31
47
  end
@@ -85,6 +101,13 @@ class FailureTest < ActiveSupport::TestCase
85
101
  end
86
102
  end
87
103
 
104
+ test 'returns to the default redirect location considering the router for supplied scope' do
105
+ call_failure app: FakeEngineApp, 'warden.options' => { scope: :user_on_engine }
106
+ assert_equal 302, @response.first
107
+ assert_equal 'You need to sign in or sign up before continuing.', @request.flash[:alert]
108
+ assert_equal 'http://test.host/user_on_engines/sign_in', @response.second['Location']
109
+ end
110
+
88
111
  if Rails.application.config.respond_to?(:relative_url_root)
89
112
  test 'returns to the default redirect location considering the relative url root' do
90
113
  swap Rails.application.config, relative_url_root: "/sample" do
@@ -271,5 +294,22 @@ class FailureTest < ActiveSupport::TestCase
271
294
  assert @response.third.body.include?('<h2>Log in</h2>')
272
295
  assert @response.third.body.include?('Your account is not activated yet.')
273
296
  end
297
+
298
+ if Rails.application.config.respond_to?(:relative_url_root)
299
+ test 'calls the original controller with the proper environment considering the relative url root' do
300
+ swap Rails.application.config, relative_url_root: "/sample" do
301
+ env = {
302
+ "warden.options" => { recall: "devise/sessions#new", attempted_path: "/sample/users/sign_in"},
303
+ "devise.mapping" => Devise.mappings[:user],
304
+ "warden" => stub_everything
305
+ }
306
+ call_failure(env)
307
+ assert @response.third.body.include?('<h2>Log in</h2>')
308
+ assert @response.third.body.include?('Invalid email or password.')
309
+ assert_equal @request.env["SCRIPT_NAME"], '/sample'
310
+ assert_equal @request.env["PATH_INFO"], '/users/sign_in'
311
+ end
312
+ end
313
+ end
274
314
  end
275
315
  end
@@ -46,6 +46,13 @@ class ViewsGeneratorTest < Rails::Generators::TestCase
46
46
  assert_no_file "app/views/devise/mailer/confirmation_instructions.html.erb"
47
47
  end
48
48
 
49
+ test "Assert mailer specific directory with simple form" do
50
+ run_generator %w(-v mailer -b simple_form_for)
51
+ assert_file "app/views/devise/mailer/confirmation_instructions.html.erb"
52
+ assert_file "app/views/devise/mailer/reset_password_instructions.html.erb"
53
+ assert_file "app/views/devise/mailer/unlock_instructions.html.erb"
54
+ end
55
+
49
56
  test "Assert specified directories with scope" do
50
57
  run_generator %w(users -v sessions)
51
58
  assert_file "app/views/users/sessions/new.html.erb"
@@ -81,4 +81,15 @@ class DatabaseAuthenticationTest < ActionDispatch::IntegrationTest
81
81
  assert_contain 'Invalid credentials'
82
82
  end
83
83
  end
84
+
85
+ test 'valid sign in calls after_database_authentication callback' do
86
+ user = create_user(email: ' foo@bar.com ')
87
+
88
+ User.expects(:find_for_database_authentication).returns user
89
+ user.expects :after_database_authentication
90
+
91
+ sign_in_as_user do
92
+ fill_in 'email', with: 'foo@bar.com'
93
+ end
94
+ end
84
95
  end
@@ -20,9 +20,11 @@ class OmniauthableIntegrationTest < ActionDispatch::IntegrationTest
20
20
  "credentials" => {"token" => 'plataformatec'},
21
21
  "extra" => {"user_hash" => FACEBOOK_INFO}
22
22
  }
23
+ OmniAuth.config.add_camelization 'facebook', 'FaceBook'
23
24
  end
24
25
 
25
26
  teardown do
27
+ OmniAuth.config.camelizations.delete('facebook')
26
28
  OmniAuth.config.test_mode = false
27
29
  end
28
30
 
@@ -40,7 +42,7 @@ class OmniauthableIntegrationTest < ActionDispatch::IntegrationTest
40
42
 
41
43
  test "can access omniauth.auth in the env hash" do
42
44
  visit "/users/sign_in"
43
- click_link "Sign in with Facebook"
45
+ click_link "Sign in with FaceBook"
44
46
 
45
47
  json = ActiveSupport::JSON.decode(response.body)
46
48
 
@@ -54,7 +56,7 @@ class OmniauthableIntegrationTest < ActionDispatch::IntegrationTest
54
56
  test "cleans up session on sign up" do
55
57
  assert_no_difference "User.count" do
56
58
  visit "/users/sign_in"
57
- click_link "Sign in with Facebook"
59
+ click_link "Sign in with FaceBook"
58
60
  end
59
61
 
60
62
  assert session["devise.facebook_data"]
@@ -75,7 +77,7 @@ class OmniauthableIntegrationTest < ActionDispatch::IntegrationTest
75
77
  test "cleans up session on cancel" do
76
78
  assert_no_difference "User.count" do
77
79
  visit "/users/sign_in"
78
- click_link "Sign in with Facebook"
80
+ click_link "Sign in with FaceBook"
79
81
  end
80
82
 
81
83
  assert session["devise.facebook_data"]
@@ -86,7 +88,7 @@ class OmniauthableIntegrationTest < ActionDispatch::IntegrationTest
86
88
  test "cleans up session on sign in" do
87
89
  assert_no_difference "User.count" do
88
90
  visit "/users/sign_in"
89
- click_link "Sign in with Facebook"
91
+ click_link "Sign in with FaceBook"
90
92
  end
91
93
 
92
94
  assert session["devise.facebook_data"]
@@ -96,13 +98,13 @@ class OmniauthableIntegrationTest < ActionDispatch::IntegrationTest
96
98
 
97
99
  test "sign in and send remember token if configured" do
98
100
  visit "/users/sign_in"
99
- click_link "Sign in with Facebook"
101
+ click_link "Sign in with FaceBook"
100
102
  assert_nil warden.cookies["remember_user_token"]
101
103
 
102
104
  stub_action!(:sign_in_facebook) do
103
105
  create_user
104
106
  visit "/users/sign_in"
105
- click_link "Sign in with Facebook"
107
+ click_link "Sign in with FaceBook"
106
108
  assert warden.authenticated?(:user)
107
109
  assert warden.cookies["remember_user_token"]
108
110
  end
@@ -118,16 +120,16 @@ class OmniauthableIntegrationTest < ActionDispatch::IntegrationTest
118
120
  OmniAuth.config.mock_auth[:facebook] = :access_denied
119
121
  visit "/users/auth/facebook/callback?error=access_denied"
120
122
  assert_current_url "/users/sign_in"
121
- assert_contain 'Could not authenticate you from Facebook because "Access denied".'
123
+ assert_contain 'Could not authenticate you from FaceBook because "Access denied".'
122
124
  end
123
125
 
124
- test "handles other exceptions from omniauth" do
126
+ test "handles other exceptions from OmniAuth" do
125
127
  OmniAuth.config.mock_auth[:facebook] = :invalid_credentials
126
128
 
127
129
  visit "/users/sign_in"
128
- click_link "Sign in with Facebook"
130
+ click_link "Sign in with FaceBook"
129
131
 
130
132
  assert_current_url "/users/sign_in"
131
- assert_contain 'Could not authenticate you from Facebook because "Invalid credentials".'
133
+ assert_contain 'Could not authenticate you from FaceBook because "Invalid credentials".'
132
134
  end
133
135
  end