devise 1.1.9 → 1.2.rc

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 (121) hide show
  1. data/CHANGELOG.rdoc +34 -26
  2. data/README.rdoc +134 -100
  3. data/app/controllers/devise/confirmations_controller.rb +1 -1
  4. data/app/controllers/devise/omniauth_callbacks_controller.rb +26 -0
  5. data/app/controllers/devise/passwords_controller.rb +1 -1
  6. data/app/controllers/devise/registrations_controller.rb +59 -6
  7. data/app/controllers/devise/sessions_controller.rb +3 -2
  8. data/app/controllers/devise/unlocks_controller.rb +1 -1
  9. data/app/helpers/devise_helper.rb +4 -2
  10. data/app/mailers/devise/mailer.rb +27 -10
  11. data/app/views/devise/confirmations/new.html.erb +1 -1
  12. data/app/views/devise/passwords/edit.html.erb +2 -2
  13. data/app/views/devise/passwords/new.html.erb +1 -1
  14. data/app/views/devise/registrations/edit.html.erb +1 -1
  15. data/app/views/devise/registrations/new.html.erb +1 -1
  16. data/app/views/devise/sessions/new.html.erb +1 -1
  17. data/app/views/devise/shared/_links.erb +6 -0
  18. data/app/views/devise/unlocks/new.html.erb +1 -1
  19. data/config/locales/en.yml +9 -2
  20. data/lib/devise.rb +116 -58
  21. data/lib/devise/controllers/helpers.rb +103 -107
  22. data/lib/devise/controllers/internal_helpers.rb +23 -7
  23. data/lib/devise/controllers/scoped_views.rb +4 -6
  24. data/lib/devise/controllers/url_helpers.rb +3 -5
  25. data/lib/devise/encryptors/base.rb +1 -1
  26. data/lib/devise/encryptors/restful_authentication_sha1.rb +4 -4
  27. data/lib/devise/failure_app.rb +29 -21
  28. data/lib/devise/hooks/forgetable.rb +2 -1
  29. data/lib/devise/hooks/rememberable.rb +11 -9
  30. data/lib/devise/mapping.rb +12 -5
  31. data/lib/devise/models.rb +0 -14
  32. data/lib/devise/models/authenticatable.rb +40 -30
  33. data/lib/devise/models/confirmable.rb +11 -15
  34. data/lib/devise/models/database_authenticatable.rb +23 -35
  35. data/lib/devise/models/encryptable.rb +65 -0
  36. data/lib/devise/models/lockable.rb +8 -7
  37. data/lib/devise/models/omniauthable.rb +23 -0
  38. data/lib/devise/models/recoverable.rb +5 -3
  39. data/lib/devise/models/registerable.rb +13 -0
  40. data/lib/devise/models/rememberable.rb +38 -30
  41. data/lib/devise/models/timeoutable.rb +20 -3
  42. data/lib/devise/models/token_authenticatable.rb +19 -7
  43. data/lib/devise/models/validatable.rb +16 -4
  44. data/lib/devise/modules.rb +15 -8
  45. data/lib/devise/omniauth.rb +47 -0
  46. data/lib/devise/omniauth/config.rb +30 -0
  47. data/lib/devise/omniauth/test_helpers.rb +57 -0
  48. data/lib/devise/omniauth/url_helpers.rb +29 -0
  49. data/lib/devise/orm/active_record.rb +2 -0
  50. data/lib/devise/orm/mongoid.rb +4 -2
  51. data/lib/devise/rails.rb +26 -46
  52. data/lib/devise/rails/routes.rb +64 -20
  53. data/lib/devise/rails/warden_compat.rb +18 -20
  54. data/lib/devise/schema.rb +13 -14
  55. data/lib/devise/strategies/authenticatable.rb +33 -7
  56. data/lib/devise/strategies/database_authenticatable.rb +1 -1
  57. data/lib/devise/strategies/rememberable.rb +1 -1
  58. data/lib/devise/strategies/token_authenticatable.rb +6 -2
  59. data/lib/devise/test_helpers.rb +11 -1
  60. data/lib/devise/version.rb +1 -1
  61. data/lib/generators/active_record/templates/migration.rb +1 -0
  62. data/lib/generators/devise/orm_helpers.rb +3 -2
  63. data/lib/generators/templates/devise.rb +70 -39
  64. data/test/controllers/helpers_test.rb +43 -67
  65. data/test/controllers/internal_helpers_test.rb +29 -8
  66. data/test/controllers/url_helpers_test.rb +2 -1
  67. data/test/failure_app_test.rb +56 -21
  68. data/test/generators/generators_test_helper.rb +4 -0
  69. data/test/generators/install_generator_test.rb +14 -0
  70. data/test/generators/views_generator_test.rb +37 -0
  71. data/test/integration/authenticatable_test.rb +147 -62
  72. data/test/integration/database_authenticatable_test.rb +22 -0
  73. data/test/integration/http_authenticatable_test.rb +12 -2
  74. data/test/integration/omniauthable_test.rb +107 -0
  75. data/test/integration/recoverable_test.rb +39 -20
  76. data/test/integration/registerable_test.rb +30 -4
  77. data/test/integration/rememberable_test.rb +57 -34
  78. data/test/integration/timeoutable_test.rb +10 -1
  79. data/test/integration/token_authenticatable_test.rb +12 -17
  80. data/test/mailers/confirmation_instructions_test.rb +4 -0
  81. data/test/mailers/reset_password_instructions_test.rb +4 -0
  82. data/test/mailers/unlock_instructions_test.rb +4 -0
  83. data/test/mapping_test.rb +37 -3
  84. data/test/models/confirmable_test.rb +3 -3
  85. data/test/models/database_authenticatable_test.rb +14 -71
  86. data/test/models/encryptable_test.rb +65 -0
  87. data/test/models/lockable_test.rb +17 -1
  88. data/test/models/recoverable_test.rb +17 -0
  89. data/test/models/rememberable_test.rb +186 -125
  90. data/test/models/token_authenticatable_test.rb +1 -13
  91. data/test/models_test.rb +5 -5
  92. data/test/omniauth/url_helpers_test.rb +47 -0
  93. data/test/rails_app/app/active_record/admin.rb +4 -1
  94. data/test/rails_app/app/active_record/user.rb +5 -4
  95. data/test/rails_app/app/controllers/{sessions_controller.rb → admins/sessions_controller.rb} +1 -1
  96. data/test/rails_app/app/controllers/home_controller.rb +9 -0
  97. data/test/rails_app/app/controllers/users/omniauth_callbacks_controller.rb +7 -0
  98. data/test/rails_app/app/mongoid/admin.rb +4 -1
  99. data/test/rails_app/app/mongoid/shim.rb +16 -3
  100. data/test/rails_app/app/mongoid/user.rb +5 -5
  101. data/test/rails_app/config/initializers/devise.rb +52 -28
  102. data/test/rails_app/config/routes.rb +14 -6
  103. data/test/rails_app/db/migrate/20100401102949_create_tables.rb +21 -17
  104. data/test/rails_app/db/schema.rb +17 -51
  105. data/test/rails_app/lib/shared_admin.rb +9 -0
  106. data/test/rails_app/lib/shared_user.rb +23 -0
  107. data/test/routes_test.rb +42 -9
  108. data/test/support/integration.rb +3 -3
  109. data/test/support/webrat/integrations/rails.rb +7 -0
  110. data/test/test_helper.rb +2 -0
  111. data/test/test_helpers_test.rb +29 -0
  112. metadata +60 -30
  113. data/Gemfile +0 -27
  114. data/Gemfile.lock +0 -115
  115. data/Rakefile +0 -55
  116. data/TODO +0 -3
  117. data/lib/devise/encryptors/bcrypt.rb +0 -19
  118. data/lib/generators/devise_install_generator.rb +0 -4
  119. data/lib/generators/devise_views_generator.rb +0 -4
  120. data/test/indifferent_hash.rb +0 -33
  121. data/test/support/test_silencer.rb +0 -5
@@ -0,0 +1,23 @@
1
+ require 'devise/omniauth'
2
+
3
+ module Devise
4
+ module Models
5
+ # Adds OmniAuth support to your model.
6
+ #
7
+ # == Options
8
+ #
9
+ # Oauthable adds the following options to devise_for:
10
+ #
11
+ # * +omniauth_providers+: Which providers are avaialble to this model. It expects an array:
12
+ #
13
+ # devise_for :database_authenticatable, :omniauthable, :omniauth_providers => [:twitter]
14
+ #
15
+ module Omniauthable
16
+ extend ActiveSupport::Concern
17
+
18
+ module ClassMethods
19
+ Devise::Models.config(self, :omniauth_providers)
20
+ end
21
+ end
22
+ end
23
+ end
@@ -1,8 +1,9 @@
1
1
  module Devise
2
2
  module Models
3
3
 
4
- # Recoverable takes care of reseting the user password and send reset instructions
5
- # Examples:
4
+ # Recoverable takes care of reseting the user password and send reset instructions.
5
+ #
6
+ # == Examples
6
7
  #
7
8
  # # resets the user password and save the record, true if valid passwords are given, otherwise false
8
9
  # User.find(1).reset_password!('password123', 'password123')
@@ -13,6 +14,7 @@ module Devise
13
14
  #
14
15
  # # creates a new token and send it with instructions about how to reset the password
15
16
  # User.find(1).send_reset_password_instructions
17
+ #
16
18
  module Recoverable
17
19
  extend ActiveSupport::Concern
18
20
 
@@ -55,7 +57,7 @@ module Devise
55
57
  # with an email not found error.
56
58
  # Attributes must contain the user email
57
59
  def send_reset_password_instructions(attributes={})
58
- recoverable = find_or_initialize_with_error_by(:email, attributes[:email], :not_found)
60
+ recoverable = find_or_initialize_with_errors(authentication_keys, attributes, :not_found)
59
61
  recoverable.send_reset_password_instructions if recoverable.persisted?
60
62
  recoverable
61
63
  end
@@ -3,6 +3,19 @@ module Devise
3
3
  # Registerable is responsible for everything related to registering a new
4
4
  # resource (ie user sign up).
5
5
  module Registerable
6
+ extend ActiveSupport::Concern
7
+
8
+ module ClassMethods
9
+ # A convenience method that receives both parameters and session to
10
+ # initialize an user. This can be used by OAuth, for example, to send
11
+ # in the user token and be stored on initialization.
12
+ #
13
+ # By default discards all information sent by the session by calling
14
+ # new with params.
15
+ def new_with_session(params, session)
16
+ new(params)
17
+ end
18
+ end
6
19
  end
7
20
  end
8
21
  end
@@ -11,24 +11,27 @@ module Devise
11
11
  # You probably wouldn't use rememberable methods directly, they are used
12
12
  # mostly internally for handling the remember token.
13
13
  #
14
- # Configuration:
14
+ # == Options
15
15
  #
16
- # remember_for: the time you want the user will be remembered without
17
- # asking for credentials. After this time the user will be
18
- # blocked and will have to enter his credentials again.
19
- # This configuration is also used to calculate the expires
20
- # time for the cookie created to remember the user.
21
- # 2.weeks by default.
16
+ # Rememberable adds the following options in devise_for:
22
17
  #
23
- # remember_across_browsers: if true, a valid remember token can be
24
- # re-used between multiple browsers.
25
- # True by default.
18
+ # * +remember_for+: the time you want the user will be remembered without
19
+ # asking for credentials. After this time the user will be blocked and
20
+ # will have to enter his credentials again. This configuration is also
21
+ # used to calculate the expires time for the cookie created to remember
22
+ # the user. By default remember_for is 2.weeks.
26
23
  #
27
- # extend_remember_period: if true, extends the user's remember period
28
- # when remembered via cookie.
29
- # False by default.
24
+ # * +remember_across_browsers+: if a valid remember token can be re-used
25
+ # between multiple browsers. By default remember_across_browsers is true
26
+ # and cannot be turned off if you are using password salt instead of remember
27
+ # token.
30
28
  #
31
- # Examples:
29
+ # * +extend_remember_period+: if true, extends the user's remember period
30
+ # when remembered via cookie. False by default.
31
+ #
32
+ # * +cookie_options+: configuration options passed to the created cookie.
33
+ #
34
+ # == Examples
32
35
  #
33
36
  # User.find(1).remember_me! # regenerating the token
34
37
  # User.find(1).forget_me! # clearing the token
@@ -49,7 +52,7 @@ module Devise
49
52
  # Generate a new remember token and save the record without validations
50
53
  # unless remember_across_browsers is true and the user already has a valid token.
51
54
  def remember_me!(extend_period=false)
52
- self.remember_token = self.class.remember_token if generate_remember_token?
55
+ self.remember_token = self.class.remember_token if respond_to?(:remember_token) && generate_remember_token?
53
56
  self.remember_created_at = Time.now.utc if generate_remember_timestamp?(extend_period)
54
57
  save(:validate => false)
55
58
  end
@@ -57,16 +60,14 @@ module Devise
57
60
  # Removes the remember token only if it exists, and save the record
58
61
  # without validations.
59
62
  def forget_me!
60
- if remember_token
61
- self.remember_token = nil
62
- self.remember_created_at = nil
63
- save(:validate => false)
64
- end
63
+ self.remember_token = nil if respond_to?(:remember_token)
64
+ self.remember_created_at = nil
65
+ save(:validate => false)
65
66
  end
66
67
 
67
68
  # Remember token should be expired if expiration time not overpass now.
68
69
  def remember_expired?
69
- remember_created_at && (remember_expires_at <= Time.now.utc)
70
+ remember_created_at.nil? || (remember_expires_at <= Time.now.utc)
70
71
  end
71
72
 
72
73
  # Remember token expires at created time + remember_for configuration
@@ -74,12 +75,20 @@ module Devise
74
75
  remember_created_at + self.class.remember_for
75
76
  end
76
77
 
77
- def cookie_domain
78
- self.class.cookie_domain
78
+ def rememberable_value
79
+ if respond_to?(:remember_token)
80
+ remember_token
81
+ elsif respond_to?(:authenticatable_salt) && (salt = authenticatable_salt)
82
+ salt
83
+ else
84
+ raise "The #{self.class.name} class does not respond to remember_token and " <<
85
+ "authenticatable_salt returns nil. In order to use rememberable, you must " <<
86
+ "add a remember_token field to your model or ensure a password is always set."
87
+ end
79
88
  end
80
89
 
81
- def cookie_domain?
82
- self.class.cookie_domain != false
90
+ def cookie_options
91
+ self.class.cookie_options
83
92
  end
84
93
 
85
94
  protected
@@ -99,14 +108,13 @@ module Devise
99
108
  module ClassMethods
100
109
  # Create the cookie key using the record id and remember_token
101
110
  def serialize_into_cookie(record)
102
- [record.id, record.remember_token]
111
+ [record.to_key, record.rememberable_value]
103
112
  end
104
113
 
105
114
  # Recreate the user based on the stored cookie
106
115
  def serialize_from_cookie(id, remember_token)
107
- conditions = { :id => id, :remember_token => remember_token }
108
- record = find(:first, :conditions => conditions)
109
- record if record && !record.remember_expired?
116
+ record = to_adapter.get(id)
117
+ record if record && record.rememberable_value == remember_token && !record.remember_expired?
110
118
  end
111
119
 
112
120
  # Generate a token checking if one does not already exist in the database.
@@ -115,7 +123,7 @@ module Devise
115
123
  end
116
124
 
117
125
  Devise::Models.config(self, :remember_for, :remember_across_browsers,
118
- :extend_remember_period, :cookie_domain)
126
+ :extend_remember_period, :cookie_options)
119
127
  end
120
128
  end
121
129
  end
@@ -7,17 +7,34 @@ module Devise
7
7
  # will be asked for credentials again, it means, he/she will be redirected
8
8
  # to the sign in page.
9
9
  #
10
- # Configuration:
10
+ # == Options
11
+ #
12
+ # Timeoutable adds the following options to devise_for:
13
+ #
14
+ # * +timeout_in+: the interval to timeout the user session without activity.
15
+ #
16
+ # == Examples
17
+ #
18
+ # user.timedout?(30.minutes.ago)
11
19
  #
12
- # timeout_in: the time you want to timeout the user session without activity.
13
20
  module Timeoutable
14
21
  extend ActiveSupport::Concern
15
22
 
16
23
  # Checks whether the user session has expired based on configured time.
17
24
  def timedout?(last_access)
25
+ return false if remember_exists_and_not_expired?
26
+
18
27
  last_access && last_access <= self.class.timeout_in.ago
19
28
  end
20
-
29
+
30
+ private
31
+
32
+ def remember_exists_and_not_expired?
33
+ return false unless respond_to?(:remember_expired?)
34
+
35
+ remember_created_at && !remember_expired?
36
+ end
37
+
21
38
  module ClassMethods
22
39
  Devise::Models.config(self, :timeout_in)
23
40
  end
@@ -5,15 +5,27 @@ module Devise
5
5
  # The TokenAuthenticatable module is responsible for generating an authentication token and
6
6
  # validating the authenticity of the same while signing in.
7
7
  #
8
- # This module only provides a few helpers to help you manage the token. Creating and resetting
9
- # the token is your responsibility.
8
+ # This module only provides a few helpers to help you manage the token, but it is up to you
9
+ # to choose how to use it. For example, if you want to have a new token every time the user
10
+ # saves his account, you can do the following:
10
11
  #
11
- # == Configuration:
12
+ # before_save :reset_authentication_token
12
13
  #
13
- # You can overwrite configuration values by setting in globally in Devise (+Devise.setup+),
14
- # using devise method, or overwriting the respective instance method.
14
+ # On the other hand, if you want to generate token unless one exists, you should use instead:
15
15
  #
16
- # +token_authentication_key+ - Defines name of the authentication token params key. E.g. /users/sign_in?some_key=...
16
+ # before_save :ensure_authentication_token
17
+ #
18
+ # If you want to delete the token after it is used, you can do so in the
19
+ # after_token_authentication callback.
20
+ #
21
+ # == Options
22
+ #
23
+ # TokenAuthenticable adds the following options to devise_for:
24
+ #
25
+ # * +token_authentication_key+: Defines name of the authentication token params key. E.g. /users/sign_in?some_key=...
26
+ #
27
+ # * +stateless_token+: By default, when you sign up with a token, Devise will store the user in session
28
+ # as any other authentication strategy. You can set stateless_token to true to avoid this.
17
29
  #
18
30
  module TokenAuthenticatable
19
31
  extend ActiveSupport::Concern
@@ -53,7 +65,7 @@ module Devise
53
65
  generate_token(:authentication_token)
54
66
  end
55
67
 
56
- ::Devise::Models.config(self, :token_authentication_key)
68
+ ::Devise::Models.config(self, :token_authentication_key, :stateless_token)
57
69
  end
58
70
  end
59
71
  end
@@ -1,10 +1,17 @@
1
1
  module Devise
2
2
  module Models
3
-
4
3
  # Validatable creates all needed validations for a user email and password.
5
4
  # It's optional, given you may want to create the validations by yourself.
6
5
  # Automatically validate if the email is present, unique and it's format is
7
- # valid. Also tests presence of password, confirmation and length
6
+ # valid. Also tests presence of password, confirmation and length.
7
+ #
8
+ # == Options
9
+ #
10
+ # Validatable adds the following options to devise_for:
11
+ #
12
+ # * +email_regexp+: the regular expression used to validate e-mails;
13
+ # * +password_length+: a range expressing password length. Defaults to 6..20.
14
+ #
8
15
  module Validatable
9
16
  # All validations used by this module.
10
17
  VALIDATIONS = [ :validates_presence_of, :validates_uniqueness_of, :validates_format_of,
@@ -15,8 +22,9 @@ module Devise
15
22
  assert_validations_api!(base)
16
23
 
17
24
  base.class_eval do
18
- validates_presence_of :email
19
- validates_uniqueness_of :email, :scope => authentication_keys[1..-1], :case_sensitive => false, :allow_blank => true
25
+ validates_presence_of :email, :if => :email_required?
26
+ validates_uniqueness_of :email, :scope => authentication_keys[1..-1],
27
+ :case_sensitive => case_insensitive_keys.exclude?(:email), :allow_blank => true
20
28
  validates_format_of :email, :with => email_regexp, :allow_blank => true
21
29
 
22
30
  with_options :if => :password_required? do |v|
@@ -45,6 +53,10 @@ module Devise
45
53
  !persisted? || !password.nil? || !password_confirmation.nil?
46
54
  end
47
55
 
56
+ def email_required?
57
+ true
58
+ end
59
+
48
60
  module ClassMethods
49
61
  Devise::Models.config(self, :email_regexp, :password_length)
50
62
  end
@@ -2,20 +2,27 @@ require 'active_support/core_ext/object/with_options'
2
2
 
3
3
  Devise.with_options :model => true do |d|
4
4
  # Strategies first
5
- d.with_options :strategy => true do |s|
6
- s.add_module :database_authenticatable, :controller => :sessions, :route => :session
7
- s.add_module :token_authenticatable, :controller => :sessions, :route => :session
5
+ d.with_options :strategy => true do |s|
6
+ routes = [nil, :new, :destroy]
7
+ s.add_module :database_authenticatable, :controller => :sessions, :route => { :session => routes }
8
+ s.add_module :token_authenticatable, :controller => :sessions, :route => { :session => routes }
8
9
  s.add_module :rememberable
9
10
  end
10
11
 
11
- # Misc after
12
- d.add_module :recoverable, :controller => :passwords, :route => :password
13
- d.add_module :registerable, :controller => :registrations, :route => :registration
12
+ # Other authentications
13
+ d.add_module :encryptable
14
+ d.add_module :omniauthable, :controller => :omniauth_callbacks, :route => :omniauth_callback
15
+
16
+ # Misc after
17
+ routes = [nil, :new, :edit]
18
+ d.add_module :recoverable, :controller => :passwords, :route => { :password => routes }
19
+ d.add_module :registerable, :controller => :registrations, :route => { :registration => (routes << :cancel) }
14
20
  d.add_module :validatable
15
21
 
16
22
  # The ones which can sign out after
17
- d.add_module :confirmable, :controller => :confirmations, :route => :confirmation
18
- d.add_module :lockable, :controller => :unlocks, :route => :unlock
23
+ routes = [nil, :new]
24
+ d.add_module :confirmable, :controller => :confirmations, :route => { :confirmation => routes }
25
+ d.add_module :lockable, :controller => :unlocks, :route => { :unlock => routes }
19
26
  d.add_module :timeoutable
20
27
 
21
28
  # Stats for last, so we make sure the user is really signed in
@@ -0,0 +1,47 @@
1
+ begin
2
+ require "omniauth/core"
3
+ rescue LoadError => e
4
+ warn "Could not load 'omniauth/core'. Please ensure you have the oa-core gem installed and listed in your Gemfile."
5
+ raise
6
+ end
7
+
8
+ module OmniAuth
9
+ # TODO HAXES Backport to OmniAuth
10
+ module Strategy #:nodoc:
11
+ def initialize(app, name, *args)
12
+ @app = app
13
+ @name = name.to_sym
14
+ @options = args.last.is_a?(Hash) ? args.pop : {}
15
+ yield self if block_given?
16
+ end
17
+
18
+ def fail!(message_key, exception = nil)
19
+ self.env['omniauth.error'] = exception
20
+ self.env['omniauth.failure_key'] = message_key
21
+ self.env['omniauth.failed_strategy'] = self
22
+ OmniAuth.config.on_failure.call(self.env, message_key.to_sym)
23
+ end
24
+ end
25
+ end
26
+
27
+ # Clean up the default path_prefix. It will be automatically set by Devise.
28
+ OmniAuth.config.path_prefix = nil
29
+
30
+ OmniAuth.config.on_failure = Proc.new do |env, key|
31
+ env['devise.mapping'] = Devise::Mapping.find_by_path!(env['PATH_INFO'], :path)
32
+ controller_klass = "#{env['devise.mapping'].controllers[:omniauth_callbacks].camelize}Controller"
33
+ controller_klass.constantize.action(:failure).call(env)
34
+ end
35
+
36
+ module Devise
37
+ module OmniAuth
38
+ autoload :Config, "devise/omniauth/config"
39
+ autoload :UrlHelpers, "devise/omniauth/url_helpers"
40
+ autoload :TestHelpers, "devise/omniauth/test_helpers"
41
+
42
+ class << self
43
+ delegate :short_circuit_authorizers!, :unshort_circuit_authorizers!,
44
+ :test_mode!, :stub!, :reset_stubs!, :to => "Devise::OmniAuth::TestHelpers"
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,30 @@
1
+ module Devise
2
+ module OmniAuth
3
+ class Config
4
+ attr_accessor :strategy
5
+ attr_reader :args
6
+
7
+ def initialize(provider, args)
8
+ @provider = provider
9
+ @args = args
10
+ @strategy = nil
11
+ end
12
+
13
+ def strategy_class
14
+ ::OmniAuth::Strategies.const_get("#{::OmniAuth::Utils.camelize(@provider.to_s)}")
15
+ end
16
+
17
+ def check_if_allow_stubs!
18
+ raise "OmniAuth strategy for #{@provider} does not allow stubs, only OAuth2 ones do." unless allow_stubs?
19
+ end
20
+
21
+ def allow_stubs?
22
+ defined?(::OmniAuth::Strategies::OAuth2) && strategy.is_a?(::OmniAuth::Strategies::OAuth2)
23
+ end
24
+
25
+ def build_connection(&block)
26
+ strategy.client.connection.build(&block)
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,57 @@
1
+ module Devise
2
+ module OmniAuth
3
+ module TestHelpers
4
+ def self.test_mode!
5
+ Faraday.default_adapter = :test if defined?(Faraday)
6
+ ActiveSupport.on_load(:action_controller) { include Devise::OmniAuth::TestHelpers }
7
+ ActiveSupport.on_load(:action_view) { include Devise::OmniAuth::TestHelpers }
8
+ end
9
+
10
+ def self.stub!(provider, stubs=nil, &block)
11
+ raise "You either need to pass stubs as a block or as a parameter" unless block_given? || stubs
12
+
13
+ config = Devise.omniauth_configs[provider]
14
+ raise "Could not find configuration for #{provider.to_s} omniauth provider" unless config
15
+
16
+ config.check_if_allow_stubs!
17
+ stubs ||= Faraday::Adapter::Test::Stubs.new(&block)
18
+
19
+ config.build_connection do |b|
20
+ b.adapter :test, stubs
21
+ end
22
+ end
23
+
24
+ def self.reset_stubs!(*providers)
25
+ target = providers.any? ? Devise.omniauth_configs.slice(*providers) : Devise.omniauth_configs
26
+ target.each_value do |config|
27
+ next unless config.allow_stubs?
28
+ config.build_connection { |b| b.adapter Faraday.default_adapter }
29
+ end
30
+ end
31
+
32
+ def self.short_circuit_authorizers!
33
+ module_eval <<-ALIASES, __FILE__, __LINE__ + 1
34
+ def omniauth_authorize_path(*args)
35
+ omniauth_callback_path(*args)
36
+ end
37
+ ALIASES
38
+
39
+ Devise.mappings.each_value do |m|
40
+ next unless m.omniauthable?
41
+
42
+ module_eval <<-ALIASES, __FILE__, __LINE__ + 1
43
+ def #{m.name}_omniauth_authorize_path(provider)
44
+ #{m.name}_omniauth_callback_path(provider)
45
+ end
46
+ ALIASES
47
+ end
48
+ end
49
+
50
+ def self.unshort_circuit_authorizers!
51
+ module_eval do
52
+ instance_methods.each { |m| remove_method(m) }
53
+ end
54
+ end
55
+ end
56
+ end
57
+ end