devise 3.0.0 → 4.8.0

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 (242) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGELOG.md +351 -0
  3. data/MIT-LICENSE +2 -1
  4. data/README.md +422 -130
  5. data/app/controllers/devise/confirmations_controller.rb +17 -6
  6. data/app/controllers/devise/omniauth_callbacks_controller.rb +12 -6
  7. data/app/controllers/devise/passwords_controller.rb +23 -8
  8. data/app/controllers/devise/registrations_controller.rb +70 -28
  9. data/app/controllers/devise/sessions_controller.rb +49 -17
  10. data/app/controllers/devise/unlocks_controller.rb +11 -4
  11. data/app/controllers/devise_controller.rb +74 -34
  12. data/app/helpers/devise_helper.rb +23 -18
  13. data/app/mailers/devise/mailer.rb +25 -10
  14. data/app/views/devise/confirmations/new.html.erb +9 -5
  15. data/app/views/devise/mailer/confirmation_instructions.html.erb +1 -1
  16. data/app/views/devise/mailer/email_changed.html.erb +7 -0
  17. data/app/views/devise/mailer/password_change.html.erb +3 -0
  18. data/app/views/devise/mailer/reset_password_instructions.html.erb +1 -1
  19. data/app/views/devise/mailer/unlock_instructions.html.erb +1 -1
  20. data/app/views/devise/passwords/edit.html.erb +16 -7
  21. data/app/views/devise/passwords/new.html.erb +9 -5
  22. data/app/views/devise/registrations/edit.html.erb +29 -15
  23. data/app/views/devise/registrations/new.html.erb +20 -9
  24. data/app/views/devise/sessions/new.html.erb +19 -10
  25. data/app/views/devise/shared/_error_messages.html.erb +15 -0
  26. data/app/views/devise/shared/{_links.erb → _links.html.erb} +10 -10
  27. data/app/views/devise/unlocks/new.html.erb +9 -5
  28. data/config/locales/en.yml +26 -20
  29. data/lib/devise/controllers/helpers.rb +122 -125
  30. data/lib/devise/controllers/rememberable.rb +14 -14
  31. data/lib/devise/controllers/scoped_views.rb +3 -1
  32. data/lib/devise/controllers/sign_in_out.rb +121 -0
  33. data/lib/devise/controllers/store_location.rb +76 -0
  34. data/lib/devise/controllers/url_helpers.rb +10 -8
  35. data/lib/devise/delegator.rb +2 -0
  36. data/lib/devise/encryptor.rb +24 -0
  37. data/lib/devise/failure_app.rb +132 -42
  38. data/lib/devise/hooks/activatable.rb +7 -6
  39. data/lib/devise/hooks/csrf_cleaner.rb +9 -0
  40. data/lib/devise/hooks/forgetable.rb +3 -1
  41. data/lib/devise/hooks/lockable.rb +5 -3
  42. data/lib/devise/hooks/proxy.rb +23 -0
  43. data/lib/devise/hooks/rememberable.rb +7 -4
  44. data/lib/devise/hooks/timeoutable.rb +18 -8
  45. data/lib/devise/hooks/trackable.rb +3 -1
  46. data/lib/devise/mailers/helpers.rb +15 -18
  47. data/lib/devise/mapping.rb +9 -3
  48. data/lib/devise/models/authenticatable.rb +102 -80
  49. data/lib/devise/models/confirmable.rb +154 -72
  50. data/lib/devise/models/database_authenticatable.rb +125 -25
  51. data/lib/devise/models/lockable.rb +50 -29
  52. data/lib/devise/models/omniauthable.rb +3 -1
  53. data/lib/devise/models/recoverable.rb +72 -50
  54. data/lib/devise/models/registerable.rb +4 -0
  55. data/lib/devise/models/rememberable.rb +65 -32
  56. data/lib/devise/models/timeoutable.rb +4 -8
  57. data/lib/devise/models/trackable.rb +20 -4
  58. data/lib/devise/models/validatable.rb +16 -9
  59. data/lib/devise/models.rb +6 -13
  60. data/lib/devise/modules.rb +12 -11
  61. data/lib/devise/omniauth/config.rb +2 -0
  62. data/lib/devise/omniauth/url_helpers.rb +14 -5
  63. data/lib/devise/omniauth.rb +4 -5
  64. data/lib/devise/orm/active_record.rb +5 -1
  65. data/lib/devise/orm/mongoid.rb +6 -2
  66. data/lib/devise/parameter_filter.rb +4 -0
  67. data/lib/devise/parameter_sanitizer.rb +144 -34
  68. data/lib/devise/rails/deprecated_constant_accessor.rb +39 -0
  69. data/lib/devise/rails/routes.rb +191 -127
  70. data/lib/devise/rails/warden_compat.rb +2 -1
  71. data/lib/devise/rails.rb +13 -20
  72. data/lib/devise/secret_key_finder.rb +27 -0
  73. data/lib/devise/strategies/authenticatable.rb +21 -22
  74. data/lib/devise/strategies/base.rb +3 -1
  75. data/lib/devise/strategies/database_authenticatable.rb +15 -4
  76. data/lib/devise/strategies/rememberable.rb +15 -3
  77. data/lib/devise/test/controller_helpers.rb +167 -0
  78. data/lib/devise/test/integration_helpers.rb +63 -0
  79. data/lib/devise/test_helpers.rb +7 -123
  80. data/lib/devise/time_inflector.rb +4 -2
  81. data/lib/devise/token_generator.rb +32 -0
  82. data/lib/devise/version.rb +3 -1
  83. data/lib/devise.rb +124 -78
  84. data/lib/generators/active_record/devise_generator.rb +64 -15
  85. data/lib/generators/active_record/templates/migration.rb +9 -8
  86. data/lib/generators/active_record/templates/migration_existing.rb +9 -8
  87. data/lib/generators/devise/controllers_generator.rb +46 -0
  88. data/lib/generators/devise/devise_generator.rb +10 -6
  89. data/lib/generators/devise/install_generator.rb +19 -1
  90. data/lib/generators/devise/orm_helpers.rb +17 -9
  91. data/lib/generators/devise/views_generator.rb +51 -28
  92. data/lib/generators/mongoid/devise_generator.rb +24 -24
  93. data/lib/generators/templates/README +13 -12
  94. data/lib/generators/templates/controllers/README +14 -0
  95. data/lib/generators/templates/controllers/confirmations_controller.rb +30 -0
  96. data/lib/generators/templates/controllers/omniauth_callbacks_controller.rb +30 -0
  97. data/lib/generators/templates/controllers/passwords_controller.rb +34 -0
  98. data/lib/generators/templates/controllers/registrations_controller.rb +62 -0
  99. data/lib/generators/templates/controllers/sessions_controller.rb +27 -0
  100. data/lib/generators/templates/controllers/unlocks_controller.rb +30 -0
  101. data/lib/generators/templates/devise.rb +118 -53
  102. data/lib/generators/templates/markerb/confirmation_instructions.markerb +1 -1
  103. data/lib/generators/templates/markerb/email_changed.markerb +7 -0
  104. data/lib/generators/templates/markerb/password_change.markerb +3 -0
  105. data/lib/generators/templates/markerb/reset_password_instructions.markerb +1 -1
  106. data/lib/generators/templates/markerb/unlock_instructions.markerb +1 -1
  107. data/lib/generators/templates/simple_form_for/confirmations/new.html.erb +6 -2
  108. data/lib/generators/templates/simple_form_for/passwords/edit.html.erb +12 -4
  109. data/lib/generators/templates/simple_form_for/passwords/new.html.erb +5 -2
  110. data/lib/generators/templates/simple_form_for/registrations/edit.html.erb +14 -6
  111. data/lib/generators/templates/simple_form_for/registrations/new.html.erb +12 -4
  112. data/lib/generators/templates/simple_form_for/sessions/new.html.erb +11 -6
  113. data/lib/generators/templates/simple_form_for/unlocks/new.html.erb +5 -2
  114. metadata +73 -294
  115. data/.gitignore +0 -10
  116. data/.travis.yml +0 -20
  117. data/.yardopts +0 -9
  118. data/CHANGELOG.rdoc +0 -941
  119. data/CONTRIBUTING.md +0 -14
  120. data/Gemfile +0 -31
  121. data/Gemfile.lock +0 -159
  122. data/Rakefile +0 -35
  123. data/app/views/devise/_links.erb +0 -3
  124. data/devise.gemspec +0 -26
  125. data/devise.png +0 -0
  126. data/gemfiles/Gemfile.rails-3.2.x +0 -31
  127. data/gemfiles/Gemfile.rails-3.2.x.lock +0 -156
  128. data/lib/devise/models/token_authenticatable.rb +0 -89
  129. data/lib/devise/strategies/token_authenticatable.rb +0 -91
  130. data/test/controllers/custom_strategy_test.rb +0 -62
  131. data/test/controllers/helpers_test.rb +0 -253
  132. data/test/controllers/internal_helpers_test.rb +0 -120
  133. data/test/controllers/passwords_controller_test.rb +0 -32
  134. data/test/controllers/sessions_controller_test.rb +0 -99
  135. data/test/controllers/url_helpers_test.rb +0 -59
  136. data/test/delegator_test.rb +0 -19
  137. data/test/devise_test.rb +0 -83
  138. data/test/failure_app_test.rb +0 -221
  139. data/test/generators/active_record_generator_test.rb +0 -73
  140. data/test/generators/devise_generator_test.rb +0 -39
  141. data/test/generators/install_generator_test.rb +0 -13
  142. data/test/generators/mongoid_generator_test.rb +0 -23
  143. data/test/generators/views_generator_test.rb +0 -67
  144. data/test/helpers/devise_helper_test.rb +0 -51
  145. data/test/integration/authenticatable_test.rb +0 -699
  146. data/test/integration/confirmable_test.rb +0 -299
  147. data/test/integration/database_authenticatable_test.rb +0 -84
  148. data/test/integration/http_authenticatable_test.rb +0 -115
  149. data/test/integration/lockable_test.rb +0 -242
  150. data/test/integration/omniauthable_test.rb +0 -133
  151. data/test/integration/recoverable_test.rb +0 -335
  152. data/test/integration/registerable_test.rb +0 -349
  153. data/test/integration/rememberable_test.rb +0 -165
  154. data/test/integration/timeoutable_test.rb +0 -150
  155. data/test/integration/token_authenticatable_test.rb +0 -205
  156. data/test/integration/trackable_test.rb +0 -92
  157. data/test/mailers/confirmation_instructions_test.rb +0 -111
  158. data/test/mailers/reset_password_instructions_test.rb +0 -92
  159. data/test/mailers/unlock_instructions_test.rb +0 -87
  160. data/test/mapping_test.rb +0 -127
  161. data/test/models/authenticatable_test.rb +0 -13
  162. data/test/models/confirmable_test.rb +0 -452
  163. data/test/models/database_authenticatable_test.rb +0 -226
  164. data/test/models/lockable_test.rb +0 -282
  165. data/test/models/omniauthable_test.rb +0 -7
  166. data/test/models/recoverable_test.rb +0 -222
  167. data/test/models/registerable_test.rb +0 -7
  168. data/test/models/rememberable_test.rb +0 -175
  169. data/test/models/serializable_test.rb +0 -49
  170. data/test/models/timeoutable_test.rb +0 -46
  171. data/test/models/token_authenticatable_test.rb +0 -55
  172. data/test/models/trackable_test.rb +0 -13
  173. data/test/models/validatable_test.rb +0 -127
  174. data/test/models_test.rb +0 -163
  175. data/test/omniauth/config_test.rb +0 -57
  176. data/test/omniauth/url_helpers_test.rb +0 -54
  177. data/test/orm/active_record.rb +0 -10
  178. data/test/orm/mongoid.rb +0 -13
  179. data/test/parameter_sanitizer_test.rb +0 -58
  180. data/test/rails_app/Rakefile +0 -6
  181. data/test/rails_app/app/active_record/admin.rb +0 -6
  182. data/test/rails_app/app/active_record/shim.rb +0 -2
  183. data/test/rails_app/app/active_record/user.rb +0 -6
  184. data/test/rails_app/app/controllers/admins/sessions_controller.rb +0 -6
  185. data/test/rails_app/app/controllers/admins_controller.rb +0 -11
  186. data/test/rails_app/app/controllers/application_controller.rb +0 -9
  187. data/test/rails_app/app/controllers/home_controller.rb +0 -25
  188. data/test/rails_app/app/controllers/publisher/registrations_controller.rb +0 -2
  189. data/test/rails_app/app/controllers/publisher/sessions_controller.rb +0 -2
  190. data/test/rails_app/app/controllers/users/omniauth_callbacks_controller.rb +0 -14
  191. data/test/rails_app/app/controllers/users_controller.rb +0 -31
  192. data/test/rails_app/app/helpers/application_helper.rb +0 -3
  193. data/test/rails_app/app/mailers/users/mailer.rb +0 -12
  194. data/test/rails_app/app/mongoid/admin.rb +0 -29
  195. data/test/rails_app/app/mongoid/shim.rb +0 -23
  196. data/test/rails_app/app/mongoid/user.rb +0 -42
  197. data/test/rails_app/app/views/admins/index.html.erb +0 -1
  198. data/test/rails_app/app/views/admins/sessions/new.html.erb +0 -2
  199. data/test/rails_app/app/views/home/admin_dashboard.html.erb +0 -1
  200. data/test/rails_app/app/views/home/index.html.erb +0 -1
  201. data/test/rails_app/app/views/home/join.html.erb +0 -1
  202. data/test/rails_app/app/views/home/private.html.erb +0 -1
  203. data/test/rails_app/app/views/home/user_dashboard.html.erb +0 -1
  204. data/test/rails_app/app/views/layouts/application.html.erb +0 -24
  205. data/test/rails_app/app/views/users/edit_form.html.erb +0 -1
  206. data/test/rails_app/app/views/users/index.html.erb +0 -1
  207. data/test/rails_app/app/views/users/mailer/confirmation_instructions.erb +0 -1
  208. data/test/rails_app/app/views/users/sessions/new.html.erb +0 -1
  209. data/test/rails_app/bin/bundle +0 -3
  210. data/test/rails_app/bin/rails +0 -4
  211. data/test/rails_app/bin/rake +0 -4
  212. data/test/rails_app/config/application.rb +0 -40
  213. data/test/rails_app/config/boot.rb +0 -8
  214. data/test/rails_app/config/database.yml +0 -18
  215. data/test/rails_app/config/environment.rb +0 -5
  216. data/test/rails_app/config/environments/development.rb +0 -34
  217. data/test/rails_app/config/environments/production.rb +0 -84
  218. data/test/rails_app/config/environments/test.rb +0 -36
  219. data/test/rails_app/config/initializers/backtrace_silencers.rb +0 -7
  220. data/test/rails_app/config/initializers/devise.rb +0 -178
  221. data/test/rails_app/config/initializers/inflections.rb +0 -2
  222. data/test/rails_app/config/initializers/secret_token.rb +0 -8
  223. data/test/rails_app/config/initializers/session_store.rb +0 -1
  224. data/test/rails_app/config/routes.rb +0 -104
  225. data/test/rails_app/config.ru +0 -4
  226. data/test/rails_app/db/migrate/20100401102949_create_tables.rb +0 -74
  227. data/test/rails_app/db/schema.rb +0 -52
  228. data/test/rails_app/lib/shared_admin.rb +0 -14
  229. data/test/rails_app/lib/shared_user.rb +0 -25
  230. data/test/rails_app/public/404.html +0 -26
  231. data/test/rails_app/public/422.html +0 -26
  232. data/test/rails_app/public/500.html +0 -26
  233. data/test/rails_app/public/favicon.ico +0 -0
  234. data/test/routes_test.rb +0 -250
  235. data/test/support/assertions.rb +0 -40
  236. data/test/support/helpers.rb +0 -91
  237. data/test/support/integration.rb +0 -92
  238. data/test/support/locale/en.yml +0 -4
  239. data/test/support/webrat/integrations/rails.rb +0 -24
  240. data/test/test_helper.rb +0 -34
  241. data/test/test_helpers_test.rb +0 -151
  242. data/test/test_models.rb +0 -26
@@ -1,13 +1,12 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require "active_support/core_ext/object/try"
2
4
  require "active_support/core_ext/hash/slice"
3
5
 
4
- module ActionDispatch::Routing
5
- class RouteSet #:nodoc:
6
- # Ensure Devise modules are included only after loading routes, because we
7
- # need devise_for mappings already declared to create filters and helpers.
8
- def finalize_with_devise!
9
- result = finalize_without_devise!
10
-
6
+ module Devise
7
+ module RouteSet
8
+ def finalize!
9
+ result = super
11
10
  @devise_finalized ||= begin
12
11
  if Devise.router_name.nil? && defined?(@devise_finalized) && self != Rails.application.try(:routes)
13
12
  warn "[DEVISE] We have detected that you are using devise_for inside engine routes. " \
@@ -21,10 +20,16 @@ module ActionDispatch::Routing
21
20
  Devise.regenerate_helpers!
22
21
  true
23
22
  end
24
-
25
23
  result
26
24
  end
27
- alias_method_chain :finalize!, :devise
25
+ end
26
+ end
27
+
28
+ module ActionDispatch::Routing
29
+ class RouteSet #:nodoc:
30
+ # Ensure Devise modules are included only after loading routes, because we
31
+ # need devise_for mappings already declared to create filters and helpers.
32
+ prepend Devise::RouteSet
28
33
  end
29
34
 
30
35
  class Mapper
@@ -43,103 +48,132 @@ module ActionDispatch::Routing
43
48
  # needed routes:
44
49
  #
45
50
  # # Session routes for Authenticatable (default)
46
- # new_user_session GET /users/sign_in {:controller=>"devise/sessions", :action=>"new"}
47
- # user_session POST /users/sign_in {:controller=>"devise/sessions", :action=>"create"}
48
- # destroy_user_session DELETE /users/sign_out {:controller=>"devise/sessions", :action=>"destroy"}
51
+ # new_user_session GET /users/sign_in {controller:"devise/sessions", action:"new"}
52
+ # user_session POST /users/sign_in {controller:"devise/sessions", action:"create"}
53
+ # destroy_user_session DELETE /users/sign_out {controller:"devise/sessions", action:"destroy"}
49
54
  #
50
55
  # # Password routes for Recoverable, if User model has :recoverable configured
51
- # new_user_password GET /users/password/new(.:format) {:controller=>"devise/passwords", :action=>"new"}
52
- # edit_user_password GET /users/password/edit(.:format) {:controller=>"devise/passwords", :action=>"edit"}
53
- # user_password PUT /users/password(.:format) {:controller=>"devise/passwords", :action=>"update"}
54
- # POST /users/password(.:format) {:controller=>"devise/passwords", :action=>"create"}
56
+ # new_user_password GET /users/password/new(.:format) {controller:"devise/passwords", action:"new"}
57
+ # edit_user_password GET /users/password/edit(.:format) {controller:"devise/passwords", action:"edit"}
58
+ # user_password PUT /users/password(.:format) {controller:"devise/passwords", action:"update"}
59
+ # POST /users/password(.:format) {controller:"devise/passwords", action:"create"}
55
60
  #
56
61
  # # Confirmation routes for Confirmable, if User model has :confirmable configured
57
- # new_user_confirmation GET /users/confirmation/new(.:format) {:controller=>"devise/confirmations", :action=>"new"}
58
- # user_confirmation GET /users/confirmation(.:format) {:controller=>"devise/confirmations", :action=>"show"}
59
- # POST /users/confirmation(.:format) {:controller=>"devise/confirmations", :action=>"create"}
62
+ # new_user_confirmation GET /users/confirmation/new(.:format) {controller:"devise/confirmations", action:"new"}
63
+ # user_confirmation GET /users/confirmation(.:format) {controller:"devise/confirmations", action:"show"}
64
+ # POST /users/confirmation(.:format) {controller:"devise/confirmations", action:"create"}
65
+ #
66
+ # ==== Routes integration
67
+ #
68
+ # +devise_for+ is meant to play nicely with other routes methods. For example,
69
+ # by calling +devise_for+ inside a namespace, it automatically nests your devise
70
+ # controllers:
71
+ #
72
+ # namespace :publisher do
73
+ # devise_for :account
74
+ # end
75
+ #
76
+ # The snippet above will use publisher/sessions controller instead of devise/sessions
77
+ # controller. You can revert this change or configure it directly by passing the :module
78
+ # option described below to +devise_for+.
79
+ #
80
+ # Also note that when you use a namespace it will affect all the helpers and methods
81
+ # for controllers and views. For example, using the above setup you'll end with
82
+ # following methods: current_publisher_account, authenticate_publisher_account!,
83
+ # publisher_account_signed_in, etc.
84
+ #
85
+ # The only aspect not affect by the router configuration is the model name. The
86
+ # model name can be explicitly set via the :class_name option.
60
87
  #
61
88
  # ==== Options
62
89
  #
63
90
  # You can configure your routes with some options:
64
91
  #
65
- # * :class_name => setup a different class to be looked up by devise, if it cannot be
92
+ # * class_name: set up a different class to be looked up by devise, if it cannot be
66
93
  # properly found by the route name.
67
94
  #
68
- # devise_for :users, :class_name => 'Account'
95
+ # devise_for :users, class_name: 'Account'
69
96
  #
70
- # * :path => allows you to setup path name that will be used, as rails routes does.
71
- # The following route configuration would setup your route as /accounts instead of /users:
97
+ # * path: allows you to set up path name that will be used, as rails routes does.
98
+ # The following route configuration would set up your route as /accounts instead of /users:
72
99
  #
73
- # devise_for :users, :path => 'accounts'
100
+ # devise_for :users, path: 'accounts'
74
101
  #
75
- # * :singular => setup the singular name for the given resource. This is used as the instance variable
76
- # name in controller, as the name in routes and the scope given to warden.
102
+ # * singular: set up the singular name for the given resource. This is used as the helper methods
103
+ # names in controller ("authenticate_#{singular}!", "#{singular}_signed_in?", "current_#{singular}"
104
+ # and "#{singular}_session"), as the scope name in routes and as the scope given to warden.
77
105
  #
78
- # devise_for :users, :singular => :user
106
+ # devise_for :admins, singular: :manager
79
107
  #
80
- # * :path_names => configure different path names to overwrite defaults :sign_in, :sign_out, :sign_up,
108
+ # devise_scope :manager do
109
+ # ...
110
+ # end
111
+ #
112
+ # class ManagerController < ApplicationController
113
+ # before_action authenticate_manager!
114
+ #
115
+ # def show
116
+ # @manager = current_manager
117
+ # ...
118
+ # end
119
+ # end
120
+ #
121
+ # * path_names: configure different path names to overwrite defaults :sign_in, :sign_out, :sign_up,
81
122
  # :password, :confirmation, :unlock.
82
123
  #
83
- # devise_for :users, :path_names => { :sign_in => 'login', :sign_out => 'logout', :password => 'secret', :confirmation => 'verification' }
124
+ # devise_for :users, path_names: {
125
+ # sign_in: 'login', sign_out: 'logout',
126
+ # password: 'secret', confirmation: 'verification',
127
+ # registration: 'register', edit: 'edit/profile'
128
+ # }
84
129
  #
85
- # * :controllers => the controller which should be used. All routes by default points to Devise controllers.
130
+ # * controllers: the controller which should be used. All routes by default points to Devise controllers.
86
131
  # However, if you want them to point to custom controller, you should do:
87
132
  #
88
- # devise_for :users, :controllers => { :sessions => "users/sessions" }
133
+ # devise_for :users, controllers: { sessions: "users/sessions" }
89
134
  #
90
- # * :failure_app => a rack app which is invoked whenever there is a failure. Strings representing a given
135
+ # * failure_app: a rack app which is invoked whenever there is a failure. Strings representing a given
91
136
  # are also allowed as parameter.
92
137
  #
93
- # * :sign_out_via => the HTTP method(s) accepted for the :sign_out action (default: :get),
138
+ # * sign_out_via: the HTTP method(s) accepted for the :sign_out action (default: :delete),
94
139
  # if you wish to restrict this to accept only :post or :delete requests you should do:
95
140
  #
96
- # devise_for :users, :sign_out_via => [ :post, :delete ]
141
+ # devise_for :users, sign_out_via: [:get, :post]
97
142
  #
98
143
  # You need to make sure that your sign_out controls trigger a request with a matching HTTP method.
99
144
  #
100
- # * :module => the namespace to find controllers (default: "devise", thus
145
+ # * module: the namespace to find controllers (default: "devise", thus
101
146
  # accessing devise/sessions, devise/registrations, and so on). If you want
102
147
  # to namespace all at once, use module:
103
148
  #
104
- # devise_for :users, :module => "users"
149
+ # devise_for :users, module: "users"
105
150
  #
106
- # Notice that whenever you use namespace in the router DSL, it automatically sets the module.
107
- # So the following setup:
151
+ # * skip: tell which controller you want to skip routes from being created.
152
+ # It accepts :all as an option, meaning it will not generate any route at all:
108
153
  #
109
- # namespace :publisher do
110
- # devise_for :account
111
- # end
154
+ # devise_for :users, skip: :sessions
112
155
  #
113
- # Will use publisher/sessions controller instead of devise/sessions controller. You can revert
114
- # this by providing the :module option to devise_for.
156
+ # * only: the opposite of :skip, tell which controllers only to generate routes to:
115
157
  #
116
- # Also pay attention that when you use a namespace it will affect all the helpers and methods for controllers
117
- # and views. For example, using the above setup you'll end with following methods:
118
- # current_publisher_account, authenticate_publisher_account!, publisher_account_signed_in, etc.
158
+ # devise_for :users, only: :sessions
119
159
  #
120
- # * :skip => tell which controller you want to skip routes from being created:
121
- #
122
- # devise_for :users, :skip => :sessions
123
- #
124
- # * :only => the opposite of :skip, tell which controllers only to generate routes to:
125
- #
126
- # devise_for :users, :only => :sessions
127
- #
128
- # * :skip_helpers => skip generating Devise url helpers like new_session_path(@user).
160
+ # * skip_helpers: skip generating Devise url helpers like new_session_path(@user).
129
161
  # This is useful to avoid conflicts with previous routes and is false by default.
130
162
  # It accepts true as option, meaning it will skip all the helpers for the controllers
131
163
  # given in :skip but it also accepts specific helpers to be skipped:
132
164
  #
133
- # devise_for :users, :skip => [:registrations, :confirmations], :skip_helpers => true
134
- # devise_for :users, :skip_helpers => [:registrations, :confirmations]
165
+ # devise_for :users, skip: [:registrations, :confirmations], skip_helpers: true
166
+ # devise_for :users, skip_helpers: [:registrations, :confirmations]
135
167
  #
136
- # * :format => include "(.:format)" in the generated routes? true by default, set to false to disable:
168
+ # * format: include "(.:format)" in the generated routes? true by default, set to false to disable:
137
169
  #
138
- # devise_for :users, :format => false
170
+ # devise_for :users, format: false
139
171
  #
140
- # * :constraints => works the same as Rails' constraints
172
+ # * constraints: works the same as Rails' constraints
141
173
  #
142
- # * :defaults => works the same as Rails' defaults
174
+ # * defaults: works the same as Rails' defaults
175
+ #
176
+ # * router_name: allows application level router name to be overwritten for the current scope
143
177
  #
144
178
  # ==== Scoping
145
179
  #
@@ -161,7 +195,7 @@ module ActionDispatch::Routing
161
195
  #
162
196
  # class ApplicationController < ActionController::Base
163
197
  # def self.default_url_options
164
- # { :locale => I18n.locale }
198
+ # { locale: I18n.locale }
165
199
  # end
166
200
  # end
167
201
  #
@@ -186,11 +220,12 @@ module ActionDispatch::Routing
186
220
  # In order to get Devise to recognize the deactivate action, your devise_scope entry should look like this:
187
221
  #
188
222
  # devise_scope :owner do
189
- # post "deactivate", :to => "registrations#deactivate", :as => "deactivate_registration"
223
+ # post "deactivate", to: "registrations#deactivate", as: "deactivate_registration"
190
224
  # end
191
225
  #
192
226
  def devise_for(*resources)
193
227
  @devise_finalized = false
228
+ raise_no_secret_key unless Devise.secret_key
194
229
  options = resources.extract_options!
195
230
 
196
231
  options[:as] ||= @scope[:as] if @scope[:as].present?
@@ -211,7 +246,7 @@ module ActionDispatch::Routing
211
246
  raise_no_devise_method_error!(mapping.class_name) unless mapping.to.respond_to?(:devise)
212
247
  rescue NameError => e
213
248
  raise unless mapping.class_name == resource.to_s.classify
214
- warn "[WARNING] You provided devise_for #{resource.inspect} but there is " <<
249
+ warn "[WARNING] You provided devise_for #{resource.inspect} but there is " \
215
250
  "no model #{mapping.class_name} defined in your application"
216
251
  next
217
252
  rescue NoMethodError => e
@@ -219,17 +254,16 @@ module ActionDispatch::Routing
219
254
  raise_no_devise_method_error!(mapping.class_name)
220
255
  end
221
256
 
222
- routes = mapping.used_routes
223
-
224
- devise_scope mapping.name do
225
- if block_given?
226
- ActiveSupport::Deprecation.warn "Passing a block to devise_for is deprecated. " \
227
- "Please remove the block from devise_for (only the block, the call to " \
228
- "devise_for must still exist) and call devise_scope :#{mapping.name} do ... end " \
229
- "with the block instead", caller
230
- yield
257
+ if options[:controllers] && options[:controllers][:omniauth_callbacks]
258
+ unless mapping.omniauthable?
259
+ raise ArgumentError, "Mapping omniauth_callbacks on a resource that is not omniauthable\n" \
260
+ "Please add `devise :omniauthable` to the `#{mapping.class_name}` model"
231
261
  end
262
+ end
263
+
264
+ routes = mapping.used_routes
232
265
 
266
+ devise_scope mapping.name do
233
267
  with_devise_exclusive_scope mapping.fullpath, mapping.name, options do
234
268
  routes.each { |mod| send("devise_#{mod}", mapping, mapping.controllers) }
235
269
  end
@@ -250,10 +284,10 @@ module ActionDispatch::Routing
250
284
  # end
251
285
  #
252
286
  # authenticate :user, lambda {|u| u.role == "admin"} do
253
- # root :to => "admin/dashboard#show", :as => :user_root
287
+ # root to: "admin/dashboard#show", as: :user_root
254
288
  # end
255
289
  #
256
- def authenticate(scope=nil, block=nil)
290
+ def authenticate(scope = nil, block = nil)
257
291
  constraints_for(:authenticate!, scope, block) do
258
292
  yield
259
293
  end
@@ -264,20 +298,20 @@ module ActionDispatch::Routing
264
298
  # a model and allows extra constraints to be done on the instance.
265
299
  #
266
300
  # authenticated :admin do
267
- # root :to => 'admin/dashboard#show', :as => :admin_root
301
+ # root to: 'admin/dashboard#show', as: :admin_root
268
302
  # end
269
303
  #
270
304
  # authenticated do
271
- # root :to => 'dashboard#show', :as => :authenticated_root
305
+ # root to: 'dashboard#show', as: :authenticated_root
272
306
  # end
273
307
  #
274
308
  # authenticated :user, lambda {|u| u.role == "admin"} do
275
- # root :to => "admin/dashboard#show", :as => :user_root
309
+ # root to: "admin/dashboard#show", as: :user_root
276
310
  # end
277
311
  #
278
- # root :to => 'landing#show'
312
+ # root to: 'landing#show'
279
313
  #
280
- def authenticated(scope=nil, block=nil)
314
+ def authenticated(scope = nil, block = nil)
281
315
  constraints_for(:authenticate?, scope, block) do
282
316
  yield
283
317
  end
@@ -288,15 +322,15 @@ module ActionDispatch::Routing
288
322
  #
289
323
  # unauthenticated do
290
324
  # as :user do
291
- # root :to => 'devise/registrations#new'
325
+ # root to: 'devise/registrations#new'
292
326
  # end
293
327
  # end
294
328
  #
295
- # root :to => 'dashboard#show'
329
+ # root to: 'dashboard#show'
296
330
  #
297
- def unauthenticated(scope=nil)
331
+ def unauthenticated(scope = nil)
298
332
  constraint = lambda do |request|
299
- not request.env["warden"].authenticate? :scope => scope
333
+ not request.env["warden"].authenticate? scope: scope
300
334
  end
301
335
 
302
336
  constraints(constraint) do
@@ -306,10 +340,10 @@ module ActionDispatch::Routing
306
340
 
307
341
  # Sets the devise scope to be used in the controller. If you have custom routes,
308
342
  # you are required to call this method (also aliased as :as) in order to specify
309
- # to which controller it is targetted.
343
+ # to which controller it is targeted.
310
344
  #
311
345
  # as :user do
312
- # get "sign_in", :to => "devise/sessions#new"
346
+ # get "sign_in", to: "devise/sessions#new"
313
347
  # end
314
348
  #
315
349
  # Notice you cannot have two scopes mapping to the same URL. And remember, if
@@ -341,41 +375,42 @@ module ActionDispatch::Routing
341
375
  protected
342
376
 
343
377
  def devise_session(mapping, controllers) #:nodoc:
344
- resource :session, :only => [], :controller => controllers[:sessions], :path => "" do
345
- get :new, :path => mapping.path_names[:sign_in], :as => "new"
346
- post :create, :path => mapping.path_names[:sign_in]
347
- match :destroy, :path => mapping.path_names[:sign_out], :as => "destroy", :via => mapping.sign_out_via
378
+ resource :session, only: [], controller: controllers[:sessions], path: "" do
379
+ get :new, path: mapping.path_names[:sign_in], as: "new"
380
+ post :create, path: mapping.path_names[:sign_in]
381
+ match :destroy, path: mapping.path_names[:sign_out], as: "destroy", via: mapping.sign_out_via
348
382
  end
349
383
  end
350
384
 
351
385
  def devise_password(mapping, controllers) #:nodoc:
352
- resource :password, :only => [:new, :create, :edit, :update],
353
- :path => mapping.path_names[:password], :controller => controllers[:passwords]
386
+ resource :password, only: [:new, :create, :edit, :update],
387
+ path: mapping.path_names[:password], controller: controllers[:passwords]
354
388
  end
355
389
 
356
390
  def devise_confirmation(mapping, controllers) #:nodoc:
357
- resource :confirmation, :only => [:new, :create, :show],
358
- :path => mapping.path_names[:confirmation], :controller => controllers[:confirmations]
391
+ resource :confirmation, only: [:new, :create, :show],
392
+ path: mapping.path_names[:confirmation], controller: controllers[:confirmations]
359
393
  end
360
394
 
361
395
  def devise_unlock(mapping, controllers) #:nodoc:
362
396
  if mapping.to.unlock_strategy_enabled?(:email)
363
- resource :unlock, :only => [:new, :create, :show],
364
- :path => mapping.path_names[:unlock], :controller => controllers[:unlocks]
397
+ resource :unlock, only: [:new, :create, :show],
398
+ path: mapping.path_names[:unlock], controller: controllers[:unlocks]
365
399
  end
366
400
  end
367
401
 
368
402
  def devise_registration(mapping, controllers) #:nodoc:
369
403
  path_names = {
370
- :new => mapping.path_names[:sign_up],
371
- :cancel => mapping.path_names[:cancel]
404
+ new: mapping.path_names[:sign_up],
405
+ edit: mapping.path_names[:edit],
406
+ cancel: mapping.path_names[:cancel]
372
407
  }
373
408
 
374
409
  options = {
375
- :only => [:new, :create, :edit, :update, :destroy],
376
- :path => mapping.path_names[:registration],
377
- :path_names => path_names,
378
- :controller => controllers[:registrations]
410
+ only: [:new, :create, :edit, :update, :destroy],
411
+ path: mapping.path_names[:registration],
412
+ path_names: path_names,
413
+ controller: controllers[:registrations]
379
414
  }
380
415
 
381
416
  resource :registration, options do
@@ -384,45 +419,64 @@ module ActionDispatch::Routing
384
419
  end
385
420
 
386
421
  def devise_omniauth_callback(mapping, controllers) #:nodoc:
387
- path, @scope[:path] = @scope[:path], nil
388
- path_prefix = Devise.omniauth_path_prefix || "/#{mapping.path}/auth".squeeze("/")
389
- set_omniauth_path_prefix!(path_prefix)
422
+ if mapping.fullpath =~ /:[a-zA-Z_]/
423
+ raise <<-ERROR
424
+ Devise does not support scoping OmniAuth callbacks under a dynamic segment
425
+ and you have set #{mapping.fullpath.inspect}. You can work around by passing
426
+ `skip: :omniauth_callbacks` to the `devise_for` call and extract omniauth
427
+ options to another `devise_for` call outside the scope. Here is an example:
428
+
429
+ devise_for :users, only: :omniauth_callbacks, controllers: {omniauth_callbacks: 'users/omniauth_callbacks'}
430
+
431
+ scope '/(:locale)', locale: /ru|en/ do
432
+ devise_for :users, skip: :omniauth_callbacks
433
+ end
434
+ ERROR
435
+ end
436
+ current_scope = @scope.dup
437
+ if @scope.respond_to? :new
438
+ @scope = @scope.new path: nil
439
+ else
440
+ @scope[:path] = nil
441
+ end
442
+ path_prefix = Devise.omniauth_path_prefix || "/#{mapping.fullpath}/auth".squeeze("/")
390
443
 
391
- providers = Regexp.union(mapping.to.omniauth_providers.map(&:to_s))
444
+ set_omniauth_path_prefix!(path_prefix)
392
445
 
393
- match "#{path_prefix}/:provider",
394
- :constraints => { :provider => providers },
395
- :to => "#{controllers[:omniauth_callbacks]}#passthru",
396
- :as => :omniauth_authorize,
397
- :via => [:get, :post]
446
+ mapping.to.omniauth_providers.each do |provider|
447
+ match "#{path_prefix}/#{provider}",
448
+ to: "#{controllers[:omniauth_callbacks]}#passthru",
449
+ as: "#{provider}_omniauth_authorize",
450
+ via: [:get, :post]
398
451
 
399
- match "#{path_prefix}/:action/callback",
400
- :constraints => { :action => providers },
401
- :to => controllers[:omniauth_callbacks],
402
- :as => :omniauth_callback,
403
- :via => [:get, :post]
452
+ match "#{path_prefix}/#{provider}/callback",
453
+ to: "#{controllers[:omniauth_callbacks]}##{provider}",
454
+ as: "#{provider}_omniauth_callback",
455
+ via: [:get, :post]
456
+ end
404
457
  ensure
405
- @scope[:path] = path
458
+ @scope = current_scope
406
459
  end
407
460
 
408
- DEVISE_SCOPE_KEYS = [:as, :path, :module, :constraints, :defaults, :options]
409
-
410
461
  def with_devise_exclusive_scope(new_path, new_as, options) #:nodoc:
411
- old = {}
412
- DEVISE_SCOPE_KEYS.each { |k| old[k] = @scope[k] }
462
+ current_scope = @scope.dup
413
463
 
414
- new = { :as => new_as, :path => new_path, :module => nil }
415
- new.merge!(options.slice(:constraints, :defaults, :options))
464
+ exclusive = { as: new_as, path: new_path, module: nil }
465
+ exclusive.merge!(options.slice(:constraints, :defaults, :options))
416
466
 
417
- @scope.merge!(new)
467
+ if @scope.respond_to? :new
468
+ @scope = @scope.new exclusive
469
+ else
470
+ exclusive.each_pair { |key, value| @scope[key] = value }
471
+ end
418
472
  yield
419
473
  ensure
420
- @scope.merge!(old)
474
+ @scope = current_scope
421
475
  end
422
476
 
423
- def constraints_for(method_to_apply, scope=nil, block=nil)
477
+ def constraints_for(method_to_apply, scope = nil, block = nil)
424
478
  constraint = lambda do |request|
425
- request.env['warden'].send(method_to_apply, :scope => scope) &&
479
+ request.env['warden'].send(method_to_apply, scope: scope) &&
426
480
  (block.nil? || block.call(request.env["warden"].user(scope)))
427
481
  end
428
482
 
@@ -442,6 +496,16 @@ module ActionDispatch::Routing
442
496
  end
443
497
  end
444
498
 
499
+ def raise_no_secret_key #:nodoc:
500
+ raise <<-ERROR
501
+ Devise.secret_key was not set. Please add the following to your Devise initializer:
502
+
503
+ config.secret_key = '#{SecureRandom.hex(64)}'
504
+
505
+ Please ensure you restarted your application after installing Devise or setting the key.
506
+ ERROR
507
+ end
508
+
445
509
  def raise_no_devise_method_error!(klass) #:nodoc:
446
510
  raise "#{klass} does not respond to 'devise' method. This usually means you haven't " \
447
511
  "loaded your ORM file or it's being loaded too late. To fix it, be sure to require 'devise/orm/YOUR_ORM' " \
@@ -1,9 +1,10 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Warden::Mixins::Common
2
4
  def request
3
5
  @request ||= ActionDispatch::Request.new(env)
4
6
  end
5
7
 
6
- # This is called internally by Warden on logout
7
8
  def reset_session!
8
9
  request.reset_session
9
10
  end
data/lib/devise/rails.rb CHANGED
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'devise/rails/routes'
2
4
  require 'devise/rails/warden_compat'
3
5
 
@@ -11,13 +13,15 @@ module Devise
11
13
  end
12
14
 
13
15
  # Force routes to be loaded if we are doing any eager load.
14
- config.before_eager_load { |app| app.reload_routes! }
16
+ config.before_eager_load do |app|
17
+ app.reload_routes! if Devise.reload_routes
18
+ end
15
19
 
16
20
  initializer "devise.url_helpers" do
17
21
  Devise.include_helpers(Devise::Controllers)
18
22
  end
19
23
 
20
- initializer "devise.omniauth" do |app|
24
+ initializer "devise.omniauth", after: :load_config_initializers, before: :build_middleware_stack do |app|
21
25
  Devise.omniauth_configs.each do |provider, config|
22
26
  app.middleware.use config.strategy_class, *config.args do |strategy|
23
27
  config.strategy = strategy
@@ -29,26 +33,15 @@ module Devise
29
33
  end
30
34
  end
31
35
 
32
- initializer "devise.mongoid_version_warning" do
33
- if defined?(Mongoid)
34
- require 'mongoid/version'
35
- if Mongoid::VERSION.to_f < 2.1
36
- puts "\n[DEVISE] Please note that Mongoid versions prior to 2.1 handle dirty model " \
37
- "object attributes in such a way that the Devise `validatable` module will not apply " \
38
- "its usual uniqueness and format validations for the email field. It is recommended " \
39
- "that you upgrade to Mongoid 2.1+ for this and other fixes, but if for some reason you " \
40
- "are unable to do so, you should add these validations manually.\n"
41
- end
42
- end
43
- end
36
+ initializer "devise.secret_key" do |app|
37
+ Devise.secret_key ||= Devise::SecretKeyFinder.new(app).find
44
38
 
45
- initializer "devise.fix_routes_proxy_missing_respond_to_bug" do
46
- # We can get rid of this once we support only Rails > 3.2
47
- ActionDispatch::Routing::RoutesProxy.class_eval do
48
- def respond_to?(method, include_private = false)
49
- super || routes.url_helpers.respond_to?(method)
39
+ Devise.token_generator ||=
40
+ if secret_key = Devise.secret_key
41
+ Devise::TokenGenerator.new(
42
+ ActiveSupport::CachingKeyGenerator.new(ActiveSupport::KeyGenerator.new(secret_key))
43
+ )
50
44
  end
51
- end
52
45
  end
53
46
  end
54
47
  end
@@ -0,0 +1,27 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Devise
4
+ class SecretKeyFinder
5
+ def initialize(application)
6
+ @application = application
7
+ end
8
+
9
+ def find
10
+ if @application.respond_to?(:credentials) && key_exists?(@application.credentials)
11
+ @application.credentials.secret_key_base
12
+ elsif @application.respond_to?(:secrets) && key_exists?(@application.secrets)
13
+ @application.secrets.secret_key_base
14
+ elsif @application.config.respond_to?(:secret_key_base) && key_exists?(@application.config)
15
+ @application.config.secret_key_base
16
+ elsif @application.respond_to?(:secret_key_base) && key_exists?(@application)
17
+ @application.secret_key_base
18
+ end
19
+ end
20
+
21
+ private
22
+
23
+ def key_exists?(object)
24
+ object.secret_key_base.present?
25
+ end
26
+ end
27
+ end