devise_invitable 2.0.2 → 2.0.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (46) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +32 -0
  3. data/README.md +696 -0
  4. data/app/controllers/devise/invitations_controller.rb +3 -3
  5. data/config/locales/ar.yml +23 -0
  6. data/config/locales/ca.yml +32 -0
  7. data/config/locales/da.yml +41 -0
  8. data/config/locales/de.yml +31 -0
  9. data/config/locales/es.yml +31 -0
  10. data/config/locales/et.yml +23 -0
  11. data/config/locales/fa.yml +31 -0
  12. data/config/locales/fr.yml +31 -0
  13. data/config/locales/id.yml +31 -0
  14. data/config/locales/it.yml +31 -0
  15. data/config/locales/ja.yml +31 -0
  16. data/config/locales/ko.yml +24 -0
  17. data/config/locales/nl.yml +32 -0
  18. data/config/locales/no.yml +17 -0
  19. data/config/locales/pl.yml +31 -0
  20. data/config/locales/pt-BR.yml +23 -0
  21. data/config/locales/pt.yml +23 -0
  22. data/config/locales/ru.yml +23 -0
  23. data/config/locales/tr.yml +24 -0
  24. data/config/locales/ua.yml +31 -0
  25. data/config/locales/vi.yml +25 -0
  26. data/config/locales/zh-CN.yml +31 -0
  27. data/config/locales/zh-HK.yml +31 -0
  28. data/config/locales/zh-TW.yml +34 -0
  29. data/lib/devise_invitable/controllers/helpers.rb +4 -0
  30. data/lib/devise_invitable/mapping.rb +4 -2
  31. data/lib/devise_invitable/models/authenticatable.rb +7 -1
  32. data/lib/devise_invitable/models.rb +16 -12
  33. data/lib/devise_invitable/version.rb +1 -1
  34. data/lib/generators/active_record/templates/migration.rb +0 -1
  35. data/lib/generators/devise_invitable/devise_invitable_generator.rb +1 -1
  36. data/test/functional/controller_helpers_test.rb +10 -0
  37. data/test/generators_test.rb +3 -2
  38. data/test/integration/invitation_test.rb +1 -1
  39. data/test/mailers/invitation_mail_test.rb +1 -1
  40. data/test/model_tests_helper.rb +1 -1
  41. data/test/models/invitable_test.rb +80 -11
  42. data/test/orm/active_record.rb +10 -5
  43. data/test/rails_app/db/migrate/20100401102949_create_tables.rb +0 -2
  44. data/test/test_helper.rb +10 -2
  45. metadata +31 -11
  46. data/README.rdoc +0 -439
@@ -0,0 +1,31 @@
1
+ zh-CN:
2
+ devise:
3
+ failure:
4
+ invited: "您有一封待处理的帐号邀请,请接受邀请完成创建您的帐号。"
5
+ invitations:
6
+ send_instructions: "邀请电子邮件已发送至 %{email}。"
7
+ invitation_token_invalid: "所提供的邀请验证无效!"
8
+ updated: "您的密码已设置成功,。现在您已经登入了。"
9
+ updated_not_active: "您的密码已设置成功。"
10
+ no_invitations_remaining: "没有待处理的邀请"
11
+ invitation_removed: "您的邀请被删除了。"
12
+ new:
13
+ header: "发送邀请"
14
+ submit_button: "发送邀请"
15
+ edit:
16
+ header: "设置您的密码"
17
+ submit_button: "设置密码"
18
+ mailer:
19
+ invitation_instructions:
20
+ subject: "邀请"
21
+ hello: "%{email} 您好"
22
+ someone_invited_you: "邀请您加入 %{url},您可以通过以下的网页链接接受邀请,并创设帐号:"
23
+ accept: "接受邀请"
24
+ accept_until: "这封邀请将于 %{due_date} 到期。"
25
+ ignore: "如果您不想接受邀请,请忽略这封电子邮件。只要未选取上述“接受邀请”的链接并且设置密码,您的帐号就不会成立。"
26
+ time:
27
+ formats:
28
+ devise:
29
+ mailer:
30
+ invitation_instructions:
31
+ accept_until_format: "%B %d, %Y %I:%M %p"
@@ -0,0 +1,31 @@
1
+ zh-HK:
2
+ devise:
3
+ failure:
4
+ invited: "你有一個待處理的邀請, 請接受它以完成創建您的帳戶。"
5
+ invitations:
6
+ send_instructions: "邀請電子郵件已發送到%{email)。"
7
+ invitation_token_invalid: "提供嘅邀請令牌無效!"
8
+ updated: "你嘅密碼設置成功。 你而家已經登錄。"
9
+ updated_not_active: "你嘅密碼設置成功。"
10
+ no_invitations_remaining: "冇剩餘邀請"
11
+ invitation_removed: "你嘅邀請已被刪除。"
12
+ new:
13
+ header: "發送邀請"
14
+ submit_button: "發送邀請"
15
+ edit:
16
+ header: "設置密碼"
17
+ submit_button: "設置密碼"
18
+ mailer:
19
+ invitation_instructions:
20
+ subject: "邀請指示"
21
+ hello: "你好%{email}"
22
+ someone_invited_you: "有人邀請你去%{url}, 你可以通過下面嘅連結接受它。"
23
+ accept: "接受邀請"
24
+ accept_until: "此邀請就喺%{due_date} 中到期。"
25
+ ignore: "如果你唔想接受邀請, 請忽略此電子郵件。 系你訪問上面的連結並設置密碼之前, 不會創建您的帳戶。"
26
+ time:
27
+ formats:
28
+ devise:
29
+ mailer:
30
+ invitation_instructions:
31
+ accept_until_format: "%B %d, %Y %I:%M %p"
@@ -0,0 +1,34 @@
1
+ zh-TW:
2
+ devise:
3
+ failure:
4
+ invited: "你有一封設立帳號的邀請,請接受邀請來創建你的帳號。"
5
+ invitations:
6
+ send_instructions: "邀請已發送至%{email)"
7
+ invitation_token_invalid: "所提供的邀請驗證無效!"
8
+ updated: "你的密碼已設置成功,現在你已經登入了。"
9
+ updated_not_active: "密碼設置成功"
10
+ no_invitations_remaining: "邀請名額已用盡"
11
+ invitation_removed: "你的邀請被刪除了"
12
+ new:
13
+ header: "發送邀請"
14
+ submit_button: "發送邀請"
15
+ edit:
16
+ header: "設置密碼"
17
+ submit_button: "設置密碼"
18
+ mailer:
19
+ invitation_instructions:
20
+ subject: "邀請"
21
+ hello: "%{email} 你好,"
22
+ someone_invited_you: “邀請你加入%{url}。你可以通過以下的網頁連結接受邀請,並創設帳號:"
23
+ accept: "接受邀請"
24
+ accept_until: "這封邀請將於 %{due_date} 到期。"
25
+ ignore:
26
+ "如果你不想接受邀請,
27
+ 請忽略這封電子郵件。只要未選取上述“接受邀請”的連結並且設置密碼,你的帳號就不會成立。"
28
+
29
+ time:
30
+ formats:
31
+ devise:
32
+ mailer:
33
+ invitation_instructions:
34
+ accept_until_format: "%B %d, %Y %I:%M %p"
@@ -12,6 +12,10 @@ module DeviseInvitable::Controllers::Helpers
12
12
  signed_in_root_path(resource)
13
13
  end
14
14
 
15
+ def invalid_token_path_for(resource_name)
16
+ after_sign_out_path_for(resource_name)
17
+ end
18
+
15
19
  protected
16
20
 
17
21
  def authenticate_inviter!
@@ -3,8 +3,10 @@ module DeviseInvitable
3
3
  private
4
4
 
5
5
  def default_controllers(options)
6
- options[:controllers] ||= {}
7
- options[:controllers][:registrations] ||= 'devise_invitable/registrations'
6
+ unless options[:module]
7
+ options[:controllers] ||= {}
8
+ options[:controllers][:registrations] ||= 'devise_invitable/registrations'
9
+ end
8
10
  super
9
11
  end
10
12
  end
@@ -1,11 +1,17 @@
1
1
  module Devise
2
2
  module Models
3
3
  module Authenticatable
4
- BLACKLIST_FOR_SERIALIZATION.concat %i[
4
+ list = %i[
5
5
  invitation_token invitation_created_at invitation_sent_at
6
6
  invitation_accepted_at invitation_limit invited_by_type
7
7
  invited_by_id invitations_count
8
8
  ]
9
+
10
+ if defined?(UNSAFE_ATTRIBUTES_FOR_SERIALIZATION)
11
+ UNSAFE_ATTRIBUTES_FOR_SERIALIZATION.concat(list)
12
+ else
13
+ BLACKLIST_FOR_SERIALIZATION.concat(list)
14
+ end
9
15
  end
10
16
  end
11
17
  end
@@ -30,12 +30,12 @@ module Devise
30
30
 
31
31
  included do
32
32
  include ::DeviseInvitable::Inviter
33
- belongs_to_options = if Devise.invited_by_class_name
34
- { class_name: Devise.invited_by_class_name }
33
+ belongs_to_options = if invited_by_class_name
34
+ { class_name: invited_by_class_name }
35
35
  else
36
36
  { polymorphic: true }
37
37
  end
38
- if fk = Devise.invited_by_foreign_key
38
+ if fk = invited_by_foreign_key
39
39
  belongs_to_options[:foreign_key] = fk
40
40
  end
41
41
  if defined?(ActiveRecord) && defined?(ActiveRecord::Base) && self < ActiveRecord::Base
@@ -76,9 +76,9 @@ module Devise
76
76
 
77
77
  def self.required_fields(klass)
78
78
  fields = [:invitation_token, :invitation_created_at, :invitation_sent_at, :invitation_accepted_at,
79
- :invitation_limit, Devise.invited_by_foreign_key || :invited_by_id, :invited_by_type]
79
+ :invitation_limit, klass.invited_by_foreign_key || :invited_by_id, :invited_by_type]
80
80
  fields << :invitations_count if defined?(ActiveRecord) && self < ActiveRecord::Base
81
- fields -= [:invited_by_type] if Devise.invited_by_class_name
81
+ fields -= [:invited_by_type] if klass.invited_by_class_name
82
82
  fields
83
83
  end
84
84
 
@@ -158,7 +158,8 @@ module Devise
158
158
  self.downcase_keys if new_record_and_responds_to?(:downcase_keys)
159
159
  self.strip_whitespace if new_record_and_responds_to?(:strip_whitespace)
160
160
 
161
- if save(validate: false)
161
+ validate = options.key?(:validate) ? options[:validate] : self.class.validate_on_invite
162
+ if save(validate: validate)
162
163
  self.invited_by.decrement_invitation_limit! if !was_invited and self.invited_by.present?
163
164
  deliver_invitation(options) unless skip_invitation
164
165
  end
@@ -194,7 +195,7 @@ module Devise
194
195
  def clear_reset_password_token
195
196
  reset_password_token_present = reset_password_token.present?
196
197
  super
197
- accept_invitation! if reset_password_token_present && invited_to_sign_up?
198
+ accept_invitation! if reset_password_token_present && valid_invitation?
198
199
  end
199
200
 
200
201
  def clear_errors_on_valid_keys
@@ -221,16 +222,16 @@ module Devise
221
222
 
222
223
  def invitation_due_at
223
224
  return nil if (self.class.invite_for == 0 || self.class.invite_for.nil?)
224
- #return nil unless self.class.invite_for
225
225
 
226
- time = self.invitation_created_at || self.invitation_sent_at
226
+ return unless (time = self.invitation_created_at || self.invitation_sent_at)
227
+
227
228
  time + self.class.invite_for
228
229
  end
229
230
 
230
231
  def add_taken_error(key)
231
232
  errors.add(key, :taken)
232
233
  end
233
-
234
+
234
235
  def invitation_taken?
235
236
  !invited_to_sign_up?
236
237
  end
@@ -324,7 +325,7 @@ module Devise
324
325
  end
325
326
 
326
327
  yield invitable if block_given?
327
- mail = invitable.invite!(nil, options) if invitable.errors.empty?
328
+ mail = invitable.invite!(nil, options.merge(validate: false)) if invitable.errors.empty?
328
329
  [invitable, mail]
329
330
  end
330
331
 
@@ -397,7 +398,10 @@ module Devise
397
398
  # lower + upper case, a digit and a symbol.
398
399
  # For more unusual rules, this method can be overridden.
399
400
  def random_password
400
- 'aA1!' + Devise.friendly_token[0, 20]
401
+ length = respond_to?(:password_length) ? password_length : Devise.password_length
402
+
403
+ prefix = 'aA1!'
404
+ prefix + Devise.friendly_token(length.last - prefix.length)
401
405
  end
402
406
  end
403
407
  end
@@ -1,3 +1,3 @@
1
1
  module DeviseInvitable
2
- VERSION = '2.0.2'.freeze
2
+ VERSION = '2.0.12'.freeze
3
3
  end
@@ -8,7 +8,6 @@ class DeviseInvitableAddTo<%= table_name.camelize %> < ActiveRecord::Migration<%
8
8
  t.integer :invitation_limit
9
9
  t.references :invited_by, polymorphic: true
10
10
  t.integer :invitations_count, default: 0
11
- t.index :invitations_count
12
11
  t.index :invitation_token, unique: true # for invitable
13
12
  t.index :invited_by_id
14
13
  end
@@ -7,7 +7,7 @@ module DeviseInvitable
7
7
 
8
8
  def inject_devise_invitable_content
9
9
  path = File.join('app', 'models', "#{file_path}.rb")
10
- inject_into_file(path, 'invitable, :', after: 'devise :') if File.exists?(path)
10
+ inject_into_file(path, 'invitable, :', after: 'devise :') if File.exist?(path)
11
11
  end
12
12
 
13
13
  hook_for :orm
@@ -41,4 +41,14 @@ class ControllerHelpersTest < ActionController::TestCase
41
41
  assert Devise::InvitationsController.method_defined? :after_accept_path_for
42
42
  assert !Devise::InvitationsController.instance_methods(false).include?(:after_accept_path_for)
43
43
  end
44
+
45
+ test 'invalid token path defaults to after sign out path' do
46
+ assert_equal @controller.send(:after_sign_out_path_for, :user), @controller.invalid_token_path_for(:user)
47
+ end
48
+
49
+ test 'invalid token path is customizable from application controller' do
50
+ custom_path = 'customized/invalid/token/path'
51
+ @controller.instance_eval "def invalid_token_path_for(resource_name) '#{custom_path}' end"
52
+ assert_equal @controller.invalid_token_path_for(:user), custom_path
53
+ end
44
54
  end
@@ -17,13 +17,14 @@ class GeneratorsTest < ActiveSupport::TestCase
17
17
 
18
18
  test "rails g devise_invitable:install" do
19
19
  @output = `cd #{RAILS_APP_PATH} && rails g devise_invitable:install -p`
20
- assert @output.match(%r{(inject|insert).* config/initializers/devise\.rb\n})
20
+ puts @output
21
+ assert @output.match(%r{(inject|insert|File unchanged! The supplied flag value not found!).* config/initializers/devise\.rb\n})
21
22
  assert @output.match(%r|create.* config/locales/devise_invitable\.en\.yml\n|)
22
23
  end
23
24
 
24
25
  test "rails g devise_invitable Octopussy" do
25
26
  @output = `cd #{RAILS_APP_PATH} && rails g devise_invitable Octopussy -p`
26
- assert @output.match(%r{(inject|insert).* app/models/octopussy\.rb\n})
27
+ assert @output.match(%r{(inject|insert|File unchanged! The supplied flag value not found!).* app/models/octopussy\.rb\n})
27
28
  assert @output.match(%r|invoke.* #{DEVISE_ORM}\n|)
28
29
  if DEVISE_ORM == :active_record
29
30
  assert @output.match(%r|create.* db/migrate/\d{14}_devise_invitable_add_to_octopussies\.rb\n|)
@@ -98,7 +98,7 @@ class InvitationTest < ActionDispatch::IntegrationTest
98
98
  fill_in 'Password confirmation', with: 'other_password'
99
99
  end
100
100
  assert_equal user_invitation_path, current_path
101
- assert page.has_css?('#error_explanation li', text: /Password .*doesn\'t match/)
101
+ assert page.has_css?('#error_explanation li', text: /Password .*doesn['’]t match/)
102
102
  assert !user.confirmed?
103
103
  end
104
104
 
@@ -102,7 +102,7 @@ class InvitationMailTest < ActionMailer::TestCase
102
102
  def initialize(*args); end
103
103
  def deliver; end
104
104
  end
105
- Devise.mailer = CustomMailer
105
+ Devise.mailer = 'InvitationMailTest::CustomMailer'
106
106
 
107
107
  User.invite!({ email: 'valid@email.com' }, nil, { invited_at: Time.now })
108
108
  end
@@ -1,6 +1,6 @@
1
1
  class ActiveSupport::TestCase
2
2
  def setup_mailer
3
- Devise.mailer = Devise::Mailer
3
+ Devise.mailer = 'Devise::Mailer'
4
4
  ActionMailer::Base.deliveries = []
5
5
  end
6
6
 
@@ -1,6 +1,10 @@
1
1
  require 'test_helper'
2
2
  require 'model_tests_helper'
3
3
 
4
+ class Validatable < User
5
+ devise :validatable, password_length: 10..20
6
+ end
7
+
4
8
  class InvitableTest < ActiveSupport::TestCase
5
9
 
6
10
  def setup
@@ -85,12 +89,12 @@ class InvitableTest < ActiveSupport::TestCase
85
89
  user.invite!
86
90
  old_invitation_created_at = 3.days.ago
87
91
  old_invitation_sent_at = 3.days.ago
88
- user.update_attributes(invitation_sent_at: old_invitation_sent_at, invitation_created_at: old_invitation_created_at)
92
+ user.update(invitation_sent_at: old_invitation_sent_at, invitation_created_at: old_invitation_created_at)
89
93
  3.times do
90
94
  user.invite!
91
95
  refute_equal old_invitation_sent_at, user.invitation_sent_at
92
96
  refute_equal old_invitation_created_at, user.invitation_created_at
93
- user.update_attributes(invitation_sent_at: old_invitation_sent_at, invitation_created_at: old_invitation_created_at)
97
+ user.update(invitation_sent_at: old_invitation_sent_at, invitation_created_at: old_invitation_created_at)
94
98
  end
95
99
  end
96
100
 
@@ -275,6 +279,23 @@ class InvitableTest < ActiveSupport::TestCase
275
279
  refute_predicate user, :invited_to_sign_up?
276
280
  end
277
281
 
282
+ test 'should not accept expired invitation while resetting the password' do
283
+ User.stubs(:invite_for).returns(1.day)
284
+ user = User.invite!(email: 'valid@email.com')
285
+ assert user.invited_to_sign_up?
286
+ user.invitation_created_at = Time.now.utc - 2.days
287
+ token, user.reset_password_token = Devise.token_generator.generate(User, :reset_password_token)
288
+ user.reset_password_sent_at = Time.now.utc
289
+ user.save
290
+
291
+ assert user.reset_password_token.present?
292
+ assert user.invitation_token.present?
293
+ User.reset_password_by_token(reset_password_token: token, password: '123456789', password_confirmation: '123456789')
294
+ assert_nil user.reload.reset_password_token
295
+ assert user.reload.invitation_token.present?
296
+ assert user.reload.invited_to_sign_up?
297
+ end
298
+
278
299
  test 'should not accept invitation on failing to reset the password' do
279
300
  user = User.invite!(email: 'valid@email.com')
280
301
  assert user.invited_to_sign_up?
@@ -362,15 +383,51 @@ class InvitableTest < ActiveSupport::TestCase
362
383
  User.validate_on_invite = validate_on_invite
363
384
  end
364
385
 
386
+ test 'should not validate other attributes when validate_on_invite is disabled (for instance method)' do
387
+ validate_on_invite = User.validate_on_invite
388
+ User.validate_on_invite = false
389
+ user = new_user(email: 'valid@email.com', username: 'a' * 50)
390
+ user.invite!(nil, validate: false)
391
+ assert_empty user.errors
392
+ User.validate_on_invite = validate_on_invite
393
+ end
394
+
395
+ test 'should validate other attributes when validate_on_invite is disabled and validate option is enabled (for instance method)' do
396
+ validate_on_invite = User.validate_on_invite
397
+ User.validate_on_invite = false
398
+ user = new_user(email: 'valid@email.com', username: 'a' * 50)
399
+ user.invite!(nil, validate: true)
400
+ refute_empty user.errors[:username]
401
+ User.validate_on_invite = validate_on_invite
402
+ end
403
+
404
+ test 'should validate other attributes when validate_on_invite is enabled and validate option is disabled (for instance method)' do
405
+ validate_on_invite = User.validate_on_invite
406
+ User.validate_on_invite = true
407
+ user = new_user(email: 'valid@email.com', username: 'a' * 50)
408
+ user.invite!
409
+ refute_empty user.errors[:username]
410
+ User.validate_on_invite = validate_on_invite
411
+ end
412
+
413
+ test 'should validate other attributes when validate_on_invite is enabled and validate option is disabled explicitly (for instance method)' do
414
+ validate_on_invite = User.validate_on_invite
415
+ User.validate_on_invite = true
416
+ user = new_user(email: 'valid@email.com', username: 'a' * 50)
417
+ user.invite!(nil, validate: false)
418
+ assert_empty user.errors
419
+ User.validate_on_invite = validate_on_invite
420
+ end
421
+
365
422
  test 'should return a record with errors if user was found by e-mail' do
366
423
  existing_user = User.new(email: 'valid@email.com')
367
424
  existing_user.save(validate: false)
368
425
  user = User.invite!(email: 'valid@email.com')
369
426
  assert_equal user, existing_user
370
- assert_equal ['has already been taken'], user.errors[:email]
427
+ assert_equal [{error: :taken}], user.errors.details[:email]
371
428
  same_user = User.invite!(email: 'valid@email.com')
372
429
  assert_equal same_user, existing_user
373
- assert_equal ['has already been taken'], same_user.errors[:email]
430
+ assert_equal [{error: :taken}], same_user.errors.details[:email]
374
431
  end
375
432
 
376
433
  test 'should return a record with errors if user with pending invitation was found by e-mail' do
@@ -384,7 +441,7 @@ class InvitableTest < ActiveSupport::TestCase
384
441
 
385
442
  user = User.invite!(email: 'valid@email.com')
386
443
  assert_equal user, existing_user
387
- assert_equal ['has already been taken'], user.errors[:email]
444
+ assert_equal [{error: :taken}], user.errors.details[:email]
388
445
  ensure
389
446
  User.resend_invitation = resend_invitation
390
447
  end
@@ -398,7 +455,7 @@ class InvitableTest < ActiveSupport::TestCase
398
455
  existing_user.save(validate: false)
399
456
  user = User.invite!(email: 'valid@email.com', username: 'a' * 50)
400
457
  assert_equal user, existing_user
401
- assert_equal ['has already been taken'], user.errors[:email]
458
+ assert_equal [{error: :taken}], user.errors.details[:email]
402
459
  refute_empty user.errors[:username]
403
460
  ensure
404
461
  User.validate_on_invite = validate_on_invite
@@ -408,13 +465,13 @@ class InvitableTest < ActiveSupport::TestCase
408
465
  test 'should return a new record with errors if e-mail is blank' do
409
466
  invited_user = User.invite!(email: '')
410
467
  assert invited_user.new_record?
411
- assert_equal ["can't be blank"], invited_user.errors[:email]
468
+ assert_equal [{error: :blank}], invited_user.errors.details[:email]
412
469
  end
413
470
 
414
471
  test 'should return a new record with errors if e-mail is invalid' do
415
472
  invited_user = User.invite!(email: 'invalid_email')
416
473
  assert invited_user.new_record?
417
- assert_equal ['is invalid'], invited_user.errors[:email]
474
+ assert_equal [{error: :invalid}], invited_user.errors.details[:email]
418
475
  end
419
476
 
420
477
  test 'should set all attributes with errors if e-mail is invalid' do
@@ -434,13 +491,13 @@ class InvitableTest < ActiveSupport::TestCase
434
491
  test 'should return a new record with errors if no invitation_token is found' do
435
492
  invited_user = User.accept_invitation!(invitation_token: 'invalid_token')
436
493
  assert invited_user.new_record?
437
- assert_equal ['is invalid'], invited_user.errors[:invitation_token]
494
+ assert_equal [{error: :invalid}], invited_user.errors.details[:invitation_token]
438
495
  end
439
496
 
440
497
  test 'should return a new record with errors if invitation_token is blank' do
441
498
  invited_user = User.accept_invitation!(invitation_token: '')
442
499
  assert invited_user.new_record?
443
- assert_equal ["can't be blank"], invited_user.errors[:invitation_token]
500
+ assert_equal [{error: :blank}], invited_user.errors.details[:invitation_token]
444
501
  end
445
502
 
446
503
  test 'should return record with errors if invitation_token has expired' do
@@ -450,7 +507,7 @@ class InvitableTest < ActiveSupport::TestCase
450
507
  invited_user.save(validate: false)
451
508
  user = User.accept_invitation!(invitation_token: Thread.current[:token])
452
509
  assert_equal user, invited_user
453
- assert_equal ['is invalid'], user.errors[:invitation_token]
510
+ assert_equal [{error: :invalid}], user.errors.details[:invitation_token]
454
511
  end
455
512
 
456
513
  test 'should allow record modification using block' do
@@ -760,4 +817,16 @@ class InvitableTest < ActiveSupport::TestCase
760
817
  assert user.persisted?
761
818
  assert user.errors.empty?
762
819
  end
820
+
821
+ test 'should set initial password following Devise.password_length' do
822
+ user = User.invite!(email: 'valid@email.com')
823
+ assert_empty user.errors
824
+ assert_equal Devise.password_length.last, user.password.length
825
+ end
826
+
827
+ test 'should set initial passsword using :validatable with custom password_length' do
828
+ user = Validatable.invite!(email: 'valid@email.com')
829
+ assert_empty user.errors
830
+ assert_equal Validatable.password_length.last, user.password.length
831
+ end
763
832
  end
@@ -1,8 +1,13 @@
1
1
  ActiveRecord::Migration.verbose = false
2
2
  ActiveRecord::Base.logger = Logger.new(nil)
3
3
 
4
- if defined? ActiveRecord::MigrationContext # rails >= 5.2
5
- ActiveRecord::MigrationContext.new(File.expand_path('../../rails_app/db/migrate/', __FILE__)).migrate
6
- else
7
- ActiveRecord::Migrator.migrate(File.expand_path('../../rails_app/db/migrate/', __FILE__))
8
- end
4
+ if ActiveRecord::VERSION::MAJOR >= 7
5
+ ActiveRecord::MigrationContext.new(
6
+ File.expand_path('../../rails_app/db/migrate/', __FILE__)
7
+ ).migrate
8
+ else # rails 6
9
+ ActiveRecord::MigrationContext.new(
10
+ File.expand_path('../../rails_app/db/migrate/', __FILE__),
11
+ ActiveRecord::Base.connection.schema_migration
12
+ ).migrate
13
+ end
@@ -32,7 +32,6 @@ class CreateTables < (Rails.version < '5.1' ? ActiveRecord::Migration : ActiveRe
32
32
  t.timestamps :null => false
33
33
  end
34
34
  add_index :users, :invitation_token, :unique => true
35
- add_index :users, :invitations_count
36
35
 
37
36
  create_table :admins do |t|
38
37
  ## Database authenticatable
@@ -41,6 +40,5 @@ class CreateTables < (Rails.version < '5.1' ? ActiveRecord::Migration : ActiveRe
41
40
 
42
41
  t.integer :invitations_count, :default => 0
43
42
  end
44
- add_index :admins, :invitations_count
45
43
  end
46
44
  end
data/test/test_helper.rb CHANGED
@@ -7,13 +7,15 @@ require "rails_app/config/environment"
7
7
  require 'rails/test_help'
8
8
  require "orm/#{DEVISE_ORM}"
9
9
  require 'capybara/rails'
10
- require 'mocha/setup'
10
+ require 'mocha/minitest'
11
11
 
12
12
  ActionMailer::Base.delivery_method = :test
13
13
  ActionMailer::Base.perform_deliveries = true
14
14
  ActionMailer::Base.default_url_options[:host] = 'example.com'
15
15
 
16
- ActiveSupport::Deprecation.silenced = true
16
+ if ActiveSupport::Deprecation.respond_to?(:silenced=)
17
+ ActiveSupport::Deprecation.silenced = true
18
+ end
17
19
  $VERBOSE = false
18
20
 
19
21
  class ActionDispatch::IntegrationTest
@@ -31,3 +33,9 @@ class ActionController::TestCase
31
33
  self.use_transactional_tests = true
32
34
  end
33
35
  end
36
+
37
+ # This is a workaround for the issue with Rails 8.0 and lazy loading of routes.
38
+ # see: https://github.com/heartcombo/devise/issues/5705
39
+ if Rails.gem_version >= Gem::Version.new('8.0')
40
+ Rails.application.routes_reloader.execute_unless_loaded
41
+ end
metadata CHANGED
@@ -1,14 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: devise_invitable
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.2
4
+ version: 2.0.12
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sergio Cambra
8
- autorequire:
9
8
  bindir: bin
10
9
  cert_chain: []
11
- date: 2020-05-06 00:00:00.000000000 Z
10
+ date: 1980-01-02 00:00:00.000000000 Z
12
11
  dependencies:
13
12
  - !ruby/object:Gem::Dependency
14
13
  name: actionmailer
@@ -44,14 +43,14 @@ dependencies:
44
43
  requirements:
45
44
  - - "~>"
46
45
  - !ruby/object:Gem::Version
47
- version: 2.0.1
46
+ version: '2.0'
48
47
  type: :development
49
48
  prerelease: false
50
49
  version_requirements: !ruby/object:Gem::Requirement
51
50
  requirements:
52
51
  - - "~>"
53
52
  - !ruby/object:Gem::Version
54
- version: 2.0.1
53
+ version: '2.0'
55
54
  description: It adds support for send invitations by email (it requires to be authenticated)
56
55
  and accept the invitation by setting a password.
57
56
  email:
@@ -62,14 +61,38 @@ extra_rdoc_files: []
62
61
  files:
63
62
  - CHANGELOG.md
64
63
  - LICENSE
65
- - README.rdoc
64
+ - README.md
66
65
  - app/controllers/devise/invitations_controller.rb
67
66
  - app/controllers/devise_invitable/registrations_controller.rb
68
67
  - app/views/devise/invitations/edit.html.erb
69
68
  - app/views/devise/invitations/new.html.erb
70
69
  - app/views/devise/mailer/invitation_instructions.html.erb
71
70
  - app/views/devise/mailer/invitation_instructions.text.erb
71
+ - config/locales/ar.yml
72
+ - config/locales/ca.yml
73
+ - config/locales/da.yml
74
+ - config/locales/de.yml
72
75
  - config/locales/en.yml
76
+ - config/locales/es.yml
77
+ - config/locales/et.yml
78
+ - config/locales/fa.yml
79
+ - config/locales/fr.yml
80
+ - config/locales/id.yml
81
+ - config/locales/it.yml
82
+ - config/locales/ja.yml
83
+ - config/locales/ko.yml
84
+ - config/locales/nl.yml
85
+ - config/locales/no.yml
86
+ - config/locales/pl.yml
87
+ - config/locales/pt-BR.yml
88
+ - config/locales/pt.yml
89
+ - config/locales/ru.yml
90
+ - config/locales/tr.yml
91
+ - config/locales/ua.yml
92
+ - config/locales/vi.yml
93
+ - config/locales/zh-CN.yml
94
+ - config/locales/zh-HK.yml
95
+ - config/locales/zh-TW.yml
73
96
  - lib/devise_invitable.rb
74
97
  - lib/devise_invitable/controllers/helpers.rb
75
98
  - lib/devise_invitable/inviter.rb
@@ -147,10 +170,9 @@ homepage: https://github.com/scambra/devise_invitable
147
170
  licenses:
148
171
  - MIT
149
172
  metadata: {}
150
- post_install_message:
151
173
  rdoc_options:
152
174
  - "--main"
153
- - README.rdoc
175
+ - README.md
154
176
  - "--charset=UTF-8"
155
177
  require_paths:
156
178
  - lib
@@ -165,9 +187,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
165
187
  - !ruby/object:Gem::Version
166
188
  version: '0'
167
189
  requirements: []
168
- rubyforge_project:
169
- rubygems_version: 2.7.9
170
- signing_key:
190
+ rubygems_version: 3.6.9
171
191
  specification_version: 4
172
192
  summary: An invitation strategy for Devise
173
193
  test_files: