doorkeeper 4.4.3 → 5.5.2

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

Potentially problematic release.


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

Files changed (282) hide show
  1. checksums.yaml +5 -5
  2. data/{NEWS.md → CHANGELOG.md} +393 -19
  3. data/README.md +97 -393
  4. data/app/assets/stylesheets/doorkeeper/admin/application.css +2 -2
  5. data/app/controllers/doorkeeper/application_controller.rb +8 -5
  6. data/app/controllers/doorkeeper/application_metal_controller.rb +7 -11
  7. data/app/controllers/doorkeeper/applications_controller.rb +62 -27
  8. data/app/controllers/doorkeeper/authorizations_controller.rb +97 -17
  9. data/app/controllers/doorkeeper/authorized_applications_controller.rb +22 -3
  10. data/app/controllers/doorkeeper/token_info_controller.rb +16 -4
  11. data/app/controllers/doorkeeper/tokens_controller.rb +98 -32
  12. data/app/helpers/doorkeeper/dashboard_helper.rb +9 -7
  13. data/app/views/doorkeeper/applications/_delete_form.html.erb +3 -1
  14. data/app/views/doorkeeper/applications/_form.html.erb +27 -26
  15. data/app/views/doorkeeper/applications/edit.html.erb +1 -1
  16. data/app/views/doorkeeper/applications/index.html.erb +17 -7
  17. data/app/views/doorkeeper/applications/new.html.erb +1 -1
  18. data/app/views/doorkeeper/applications/show.html.erb +38 -17
  19. data/app/views/doorkeeper/authorizations/error.html.erb +1 -1
  20. data/app/views/doorkeeper/authorizations/form_post.html.erb +15 -0
  21. data/app/views/doorkeeper/authorizations/new.html.erb +6 -0
  22. data/app/views/layouts/doorkeeper/admin.html.erb +16 -14
  23. data/config/locales/en.yml +23 -3
  24. data/lib/doorkeeper/config/abstract_builder.rb +28 -0
  25. data/lib/doorkeeper/config/option.rb +82 -0
  26. data/lib/doorkeeper/config/validations.rb +53 -0
  27. data/lib/doorkeeper/config.rb +471 -140
  28. data/lib/doorkeeper/engine.rb +8 -2
  29. data/lib/doorkeeper/errors.rb +25 -16
  30. data/lib/doorkeeper/grant_flow/fallback_flow.rb +15 -0
  31. data/lib/doorkeeper/grant_flow/flow.rb +44 -0
  32. data/lib/doorkeeper/grant_flow/registry.rb +50 -0
  33. data/lib/doorkeeper/grant_flow.rb +45 -0
  34. data/lib/doorkeeper/grape/authorization_decorator.rb +6 -4
  35. data/lib/doorkeeper/grape/helpers.rb +13 -7
  36. data/lib/doorkeeper/helpers/controller.rb +43 -10
  37. data/lib/doorkeeper/models/access_grant_mixin.rb +97 -3
  38. data/lib/doorkeeper/models/access_token_mixin.rb +272 -66
  39. data/lib/doorkeeper/models/application_mixin.rb +50 -5
  40. data/lib/doorkeeper/models/concerns/accessible.rb +2 -0
  41. data/lib/doorkeeper/models/concerns/expirable.rb +7 -3
  42. data/lib/doorkeeper/models/concerns/orderable.rb +2 -0
  43. data/lib/doorkeeper/models/concerns/ownership.rb +4 -7
  44. data/lib/doorkeeper/models/concerns/resource_ownerable.rb +47 -0
  45. data/lib/doorkeeper/models/concerns/reusable.rb +19 -0
  46. data/lib/doorkeeper/models/concerns/revocable.rb +3 -27
  47. data/lib/doorkeeper/models/concerns/scopes.rb +12 -2
  48. data/lib/doorkeeper/models/concerns/secret_storable.rb +106 -0
  49. data/lib/doorkeeper/oauth/authorization/code.rb +48 -12
  50. data/lib/doorkeeper/oauth/authorization/context.rb +17 -0
  51. data/lib/doorkeeper/oauth/authorization/token.rb +58 -24
  52. data/lib/doorkeeper/oauth/authorization/uri_builder.rb +7 -5
  53. data/lib/doorkeeper/oauth/authorization_code_request.rb +58 -10
  54. data/lib/doorkeeper/oauth/base_request.rb +35 -24
  55. data/lib/doorkeeper/oauth/base_response.rb +2 -0
  56. data/lib/doorkeeper/oauth/client/credentials.rb +5 -5
  57. data/lib/doorkeeper/oauth/client.rb +10 -11
  58. data/lib/doorkeeper/oauth/client_credentials/creator.rb +47 -4
  59. data/lib/doorkeeper/oauth/client_credentials/issuer.rb +16 -9
  60. data/lib/doorkeeper/oauth/client_credentials/validator.rb +56 -0
  61. data/lib/doorkeeper/oauth/client_credentials_request.rb +10 -11
  62. data/lib/doorkeeper/oauth/code_request.rb +8 -12
  63. data/lib/doorkeeper/oauth/code_response.rb +27 -15
  64. data/lib/doorkeeper/oauth/error.rb +3 -1
  65. data/lib/doorkeeper/oauth/error_response.rb +35 -14
  66. data/lib/doorkeeper/oauth/forbidden_token_response.rb +10 -3
  67. data/lib/doorkeeper/oauth/helpers/scope_checker.rb +23 -18
  68. data/lib/doorkeeper/oauth/helpers/unique_token.rb +20 -3
  69. data/lib/doorkeeper/oauth/helpers/uri_checker.rb +42 -7
  70. data/lib/doorkeeper/oauth/hooks/context.rb +21 -0
  71. data/lib/doorkeeper/oauth/invalid_request_response.rb +43 -0
  72. data/lib/doorkeeper/oauth/invalid_token_response.rb +29 -4
  73. data/lib/doorkeeper/oauth/nonstandard.rb +39 -0
  74. data/lib/doorkeeper/oauth/password_access_token_request.rb +43 -10
  75. data/lib/doorkeeper/oauth/pre_authorization.rb +133 -26
  76. data/lib/doorkeeper/oauth/refresh_token_request.rb +59 -31
  77. data/lib/doorkeeper/oauth/scopes.rb +8 -4
  78. data/lib/doorkeeper/oauth/token.rb +12 -8
  79. data/lib/doorkeeper/oauth/token_introspection.rb +97 -23
  80. data/lib/doorkeeper/oauth/token_request.rb +8 -20
  81. data/lib/doorkeeper/oauth/token_response.rb +14 -10
  82. data/lib/doorkeeper/oauth.rb +13 -0
  83. data/lib/doorkeeper/orm/active_record/access_grant.rb +5 -30
  84. data/lib/doorkeeper/orm/active_record/access_token.rb +5 -43
  85. data/lib/doorkeeper/orm/active_record/application.rb +6 -57
  86. data/lib/doorkeeper/orm/active_record/mixins/access_grant.rb +68 -0
  87. data/lib/doorkeeper/orm/active_record/mixins/access_token.rb +59 -0
  88. data/lib/doorkeeper/orm/active_record/mixins/application.rb +198 -0
  89. data/lib/doorkeeper/orm/active_record/redirect_uri_validator.rb +66 -0
  90. data/lib/doorkeeper/orm/active_record/stale_records_cleaner.rb +33 -0
  91. data/lib/doorkeeper/orm/active_record.rb +27 -9
  92. data/lib/doorkeeper/rails/helpers.rb +10 -8
  93. data/lib/doorkeeper/rails/routes/abstract_router.rb +35 -0
  94. data/lib/doorkeeper/rails/routes/mapper.rb +4 -2
  95. data/lib/doorkeeper/rails/routes/mapping.rb +9 -7
  96. data/lib/doorkeeper/rails/routes/registry.rb +45 -0
  97. data/lib/doorkeeper/rails/routes.rb +37 -30
  98. data/lib/doorkeeper/rake/db.rake +40 -0
  99. data/lib/doorkeeper/rake/setup.rake +11 -0
  100. data/lib/doorkeeper/rake.rb +14 -0
  101. data/lib/doorkeeper/request/authorization_code.rb +6 -4
  102. data/lib/doorkeeper/request/client_credentials.rb +3 -3
  103. data/lib/doorkeeper/request/code.rb +1 -1
  104. data/lib/doorkeeper/request/password.rb +4 -3
  105. data/lib/doorkeeper/request/refresh_token.rb +6 -5
  106. data/lib/doorkeeper/request/strategy.rb +4 -2
  107. data/lib/doorkeeper/request/token.rb +1 -1
  108. data/lib/doorkeeper/request.rb +61 -34
  109. data/lib/doorkeeper/secret_storing/base.rb +64 -0
  110. data/lib/doorkeeper/secret_storing/bcrypt.rb +60 -0
  111. data/lib/doorkeeper/secret_storing/plain.rb +33 -0
  112. data/lib/doorkeeper/secret_storing/sha256_hash.rb +26 -0
  113. data/lib/doorkeeper/server.rb +9 -11
  114. data/lib/doorkeeper/stale_records_cleaner.rb +24 -0
  115. data/lib/doorkeeper/validations.rb +2 -0
  116. data/lib/doorkeeper/version.rb +7 -29
  117. data/lib/doorkeeper.rb +111 -64
  118. data/lib/generators/doorkeeper/application_owner_generator.rb +24 -18
  119. data/lib/generators/doorkeeper/confidential_applications_generator.rb +33 -0
  120. data/lib/generators/doorkeeper/enable_polymorphic_resource_owner_generator.rb +39 -0
  121. data/lib/generators/doorkeeper/install_generator.rb +19 -9
  122. data/lib/generators/doorkeeper/migration_generator.rb +23 -18
  123. data/lib/generators/doorkeeper/pkce_generator.rb +33 -0
  124. data/lib/generators/doorkeeper/previous_refresh_token_generator.rb +28 -22
  125. data/{spec/dummy/db/migrate/20180210183654_add_confidential_to_application.rb → lib/generators/doorkeeper/templates/add_confidential_to_applications.rb.erb} +2 -2
  126. data/lib/generators/doorkeeper/templates/add_owner_to_application_migration.rb.erb +3 -1
  127. data/lib/generators/doorkeeper/templates/add_previous_refresh_token_to_access_tokens.rb.erb +2 -0
  128. data/lib/generators/doorkeeper/templates/enable_pkce_migration.rb.erb +8 -0
  129. data/lib/generators/doorkeeper/templates/enable_polymorphic_resource_owner_migration.rb.erb +17 -0
  130. data/lib/generators/doorkeeper/templates/initializer.rb +382 -30
  131. data/lib/generators/doorkeeper/templates/migration.rb.erb +35 -16
  132. data/lib/generators/doorkeeper/views_generator.rb +8 -4
  133. data/vendor/assets/stylesheets/doorkeeper/bootstrap.min.css +4 -5
  134. metadata +95 -309
  135. data/.coveralls.yml +0 -1
  136. data/.github/ISSUE_TEMPLATE.md +0 -25
  137. data/.github/PULL_REQUEST_TEMPLATE.md +0 -17
  138. data/.gitignore +0 -19
  139. data/.hound.yml +0 -2
  140. data/.rspec +0 -1
  141. data/.rubocop.yml +0 -17
  142. data/.travis.yml +0 -38
  143. data/Appraisals +0 -18
  144. data/CODE_OF_CONDUCT.md +0 -46
  145. data/CONTRIBUTING.md +0 -47
  146. data/Gemfile +0 -10
  147. data/RELEASING.md +0 -10
  148. data/Rakefile +0 -20
  149. data/SECURITY.md +0 -15
  150. data/app/validators/redirect_uri_validator.rb +0 -44
  151. data/doorkeeper.gemspec +0 -32
  152. data/gemfiles/rails_4_2.gemfile +0 -13
  153. data/gemfiles/rails_5_0.gemfile +0 -12
  154. data/gemfiles/rails_5_1.gemfile +0 -12
  155. data/gemfiles/rails_5_2.gemfile +0 -12
  156. data/gemfiles/rails_master.gemfile +0 -14
  157. data/lib/doorkeeper/oauth/client_credentials/validation.rb +0 -45
  158. data/lib/generators/doorkeeper/add_client_confidentiality_generator.rb +0 -31
  159. data/lib/generators/doorkeeper/templates/add_confidential_to_application_migration.rb.erb +0 -11
  160. data/spec/controllers/application_metal_controller.rb +0 -10
  161. data/spec/controllers/applications_controller_spec.rb +0 -69
  162. data/spec/controllers/authorizations_controller_spec.rb +0 -250
  163. data/spec/controllers/protected_resources_controller_spec.rb +0 -309
  164. data/spec/controllers/token_info_controller_spec.rb +0 -56
  165. data/spec/controllers/tokens_controller_spec.rb +0 -274
  166. data/spec/dummy/Rakefile +0 -7
  167. data/spec/dummy/app/controllers/application_controller.rb +0 -3
  168. data/spec/dummy/app/controllers/custom_authorizations_controller.rb +0 -7
  169. data/spec/dummy/app/controllers/full_protected_resources_controller.rb +0 -12
  170. data/spec/dummy/app/controllers/home_controller.rb +0 -17
  171. data/spec/dummy/app/controllers/metal_controller.rb +0 -11
  172. data/spec/dummy/app/controllers/semi_protected_resources_controller.rb +0 -11
  173. data/spec/dummy/app/helpers/application_helper.rb +0 -5
  174. data/spec/dummy/app/models/user.rb +0 -5
  175. data/spec/dummy/app/views/home/index.html.erb +0 -0
  176. data/spec/dummy/app/views/layouts/application.html.erb +0 -14
  177. data/spec/dummy/config/application.rb +0 -23
  178. data/spec/dummy/config/boot.rb +0 -9
  179. data/spec/dummy/config/database.yml +0 -15
  180. data/spec/dummy/config/environment.rb +0 -5
  181. data/spec/dummy/config/environments/development.rb +0 -29
  182. data/spec/dummy/config/environments/production.rb +0 -62
  183. data/spec/dummy/config/environments/test.rb +0 -44
  184. data/spec/dummy/config/initializers/backtrace_silencers.rb +0 -7
  185. data/spec/dummy/config/initializers/doorkeeper.rb +0 -112
  186. data/spec/dummy/config/initializers/new_framework_defaults.rb +0 -6
  187. data/spec/dummy/config/initializers/secret_token.rb +0 -8
  188. data/spec/dummy/config/initializers/session_store.rb +0 -8
  189. data/spec/dummy/config/initializers/wrap_parameters.rb +0 -14
  190. data/spec/dummy/config/locales/doorkeeper.en.yml +0 -5
  191. data/spec/dummy/config/routes.rb +0 -52
  192. data/spec/dummy/config.ru +0 -4
  193. data/spec/dummy/db/migrate/20111122132257_create_users.rb +0 -11
  194. data/spec/dummy/db/migrate/20120312140401_add_password_to_users.rb +0 -7
  195. data/spec/dummy/db/migrate/20151223192035_create_doorkeeper_tables.rb +0 -62
  196. data/spec/dummy/db/migrate/20151223200000_add_owner_to_application.rb +0 -9
  197. data/spec/dummy/db/migrate/20160320211015_add_previous_refresh_token_to_access_tokens.rb +0 -13
  198. data/spec/dummy/db/schema.rb +0 -68
  199. data/spec/dummy/public/404.html +0 -26
  200. data/spec/dummy/public/422.html +0 -26
  201. data/spec/dummy/public/500.html +0 -26
  202. data/spec/dummy/public/favicon.ico +0 -0
  203. data/spec/dummy/script/rails +0 -6
  204. data/spec/factories.rb +0 -28
  205. data/spec/generators/application_owner_generator_spec.rb +0 -41
  206. data/spec/generators/install_generator_spec.rb +0 -31
  207. data/spec/generators/migration_generator_spec.rb +0 -41
  208. data/spec/generators/previous_refresh_token_generator_spec.rb +0 -57
  209. data/spec/generators/templates/routes.rb +0 -3
  210. data/spec/generators/views_generator_spec.rb +0 -27
  211. data/spec/grape/grape_integration_spec.rb +0 -135
  212. data/spec/helpers/doorkeeper/dashboard_helper_spec.rb +0 -24
  213. data/spec/lib/config_spec.rb +0 -462
  214. data/spec/lib/doorkeeper_spec.rb +0 -150
  215. data/spec/lib/models/expirable_spec.rb +0 -50
  216. data/spec/lib/models/revocable_spec.rb +0 -59
  217. data/spec/lib/models/scopes_spec.rb +0 -43
  218. data/spec/lib/oauth/authorization/uri_builder_spec.rb +0 -41
  219. data/spec/lib/oauth/authorization_code_request_spec.rb +0 -123
  220. data/spec/lib/oauth/base_request_spec.rb +0 -155
  221. data/spec/lib/oauth/base_response_spec.rb +0 -45
  222. data/spec/lib/oauth/client/credentials_spec.rb +0 -90
  223. data/spec/lib/oauth/client_credentials/creator_spec.rb +0 -44
  224. data/spec/lib/oauth/client_credentials/issuer_spec.rb +0 -86
  225. data/spec/lib/oauth/client_credentials/validation_spec.rb +0 -54
  226. data/spec/lib/oauth/client_credentials_integration_spec.rb +0 -27
  227. data/spec/lib/oauth/client_credentials_request_spec.rb +0 -105
  228. data/spec/lib/oauth/client_spec.rb +0 -39
  229. data/spec/lib/oauth/code_request_spec.rb +0 -43
  230. data/spec/lib/oauth/code_response_spec.rb +0 -34
  231. data/spec/lib/oauth/error_response_spec.rb +0 -61
  232. data/spec/lib/oauth/error_spec.rb +0 -23
  233. data/spec/lib/oauth/forbidden_token_response_spec.rb +0 -23
  234. data/spec/lib/oauth/helpers/scope_checker_spec.rb +0 -64
  235. data/spec/lib/oauth/helpers/unique_token_spec.rb +0 -20
  236. data/spec/lib/oauth/helpers/uri_checker_spec.rb +0 -218
  237. data/spec/lib/oauth/invalid_token_response_spec.rb +0 -56
  238. data/spec/lib/oauth/password_access_token_request_spec.rb +0 -96
  239. data/spec/lib/oauth/pre_authorization_spec.rb +0 -160
  240. data/spec/lib/oauth/refresh_token_request_spec.rb +0 -166
  241. data/spec/lib/oauth/scopes_spec.rb +0 -149
  242. data/spec/lib/oauth/token_request_spec.rb +0 -96
  243. data/spec/lib/oauth/token_response_spec.rb +0 -85
  244. data/spec/lib/oauth/token_spec.rb +0 -116
  245. data/spec/lib/request/strategy_spec.rb +0 -53
  246. data/spec/lib/server_spec.rb +0 -59
  247. data/spec/models/doorkeeper/access_grant_spec.rb +0 -36
  248. data/spec/models/doorkeeper/access_token_spec.rb +0 -418
  249. data/spec/models/doorkeeper/application_spec.rb +0 -303
  250. data/spec/requests/applications/applications_request_spec.rb +0 -94
  251. data/spec/requests/applications/authorized_applications_spec.rb +0 -30
  252. data/spec/requests/endpoints/authorization_spec.rb +0 -71
  253. data/spec/requests/endpoints/token_spec.rb +0 -71
  254. data/spec/requests/flows/authorization_code_errors_spec.rb +0 -76
  255. data/spec/requests/flows/authorization_code_spec.rb +0 -149
  256. data/spec/requests/flows/client_credentials_spec.rb +0 -86
  257. data/spec/requests/flows/implicit_grant_errors_spec.rb +0 -32
  258. data/spec/requests/flows/implicit_grant_spec.rb +0 -61
  259. data/spec/requests/flows/password_spec.rb +0 -197
  260. data/spec/requests/flows/refresh_token_spec.rb +0 -174
  261. data/spec/requests/flows/revoke_token_spec.rb +0 -157
  262. data/spec/requests/flows/skip_authorization_spec.rb +0 -59
  263. data/spec/requests/protected_resources/metal_spec.rb +0 -14
  264. data/spec/requests/protected_resources/private_api_spec.rb +0 -81
  265. data/spec/routing/custom_controller_routes_spec.rb +0 -75
  266. data/spec/routing/default_routes_spec.rb +0 -39
  267. data/spec/routing/scoped_routes_spec.rb +0 -31
  268. data/spec/spec_helper.rb +0 -4
  269. data/spec/spec_helper_integration.rb +0 -74
  270. data/spec/support/dependencies/factory_girl.rb +0 -2
  271. data/spec/support/helpers/access_token_request_helper.rb +0 -11
  272. data/spec/support/helpers/authorization_request_helper.rb +0 -41
  273. data/spec/support/helpers/config_helper.rb +0 -9
  274. data/spec/support/helpers/model_helper.rb +0 -72
  275. data/spec/support/helpers/request_spec_helper.rb +0 -88
  276. data/spec/support/helpers/url_helper.rb +0 -56
  277. data/spec/support/http_method_shim.rb +0 -38
  278. data/spec/support/orm/active_record.rb +0 -3
  279. data/spec/support/shared/controllers_shared_context.rb +0 -65
  280. data/spec/support/shared/models_shared_examples.rb +0 -52
  281. data/spec/validators/redirect_uri_validator_spec.rb +0 -123
  282. data/spec/version/version_spec.rb +0 -15
@@ -0,0 +1,66 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "uri"
4
+
5
+ module Doorkeeper
6
+ # ActiveModel validator for redirect URI validation in according
7
+ # to OAuth standards and Doorkeeper configuration.
8
+ class RedirectUriValidator < ActiveModel::EachValidator
9
+ def validate_each(record, attribute, value)
10
+ if value.blank?
11
+ return if Doorkeeper.config.allow_blank_redirect_uri?(record)
12
+
13
+ record.errors.add(attribute, :blank)
14
+ else
15
+ value.split.each do |val|
16
+ next if oob_redirect_uri?(val)
17
+
18
+ uri = ::URI.parse(val)
19
+ record.errors.add(attribute, :forbidden_uri) if forbidden_uri?(uri)
20
+ record.errors.add(attribute, :fragment_present) unless uri.fragment.nil?
21
+ record.errors.add(attribute, :unspecified_scheme) if unspecified_scheme?(uri)
22
+ record.errors.add(attribute, :relative_uri) if relative_uri?(uri)
23
+ record.errors.add(attribute, :secured_uri) if invalid_ssl_uri?(uri)
24
+ record.errors.add(attribute, :invalid_uri) if unspecified_host?(uri)
25
+ end
26
+ end
27
+ rescue URI::InvalidURIError
28
+ record.errors.add(attribute, :invalid_uri)
29
+ end
30
+
31
+ private
32
+
33
+ def oob_redirect_uri?(uri)
34
+ Doorkeeper::OAuth::NonStandard::IETF_WG_OAUTH2_OOB_METHODS.include?(uri)
35
+ end
36
+
37
+ def forbidden_uri?(uri)
38
+ Doorkeeper.config.forbid_redirect_uri.call(uri)
39
+ end
40
+
41
+ def unspecified_scheme?(uri)
42
+ return true if uri.opaque.present?
43
+
44
+ %w[localhost].include?(uri.try(:scheme))
45
+ end
46
+
47
+ def unspecified_host?(uri)
48
+ uri.is_a?(URI::HTTP) && uri.host.nil?
49
+ end
50
+
51
+ def relative_uri?(uri)
52
+ uri.scheme.nil? && uri.host.nil?
53
+ end
54
+
55
+ def invalid_ssl_uri?(uri)
56
+ forces_ssl = Doorkeeper.config.force_ssl_in_redirect_uri
57
+ non_https = uri.try(:scheme) == "http"
58
+
59
+ if forces_ssl.respond_to?(:call)
60
+ forces_ssl.call(uri) && non_https
61
+ else
62
+ forces_ssl && non_https
63
+ end
64
+ end
65
+ end
66
+ end
@@ -0,0 +1,33 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Doorkeeper
4
+ module Orm
5
+ module ActiveRecord
6
+ # Helper class to clear stale and non-active tokens and grants.
7
+ # Used by Doorkeeper Rake tasks.
8
+ #
9
+ class StaleRecordsCleaner
10
+ def initialize(base_scope)
11
+ @base_scope = base_scope
12
+ end
13
+
14
+ # Clears revoked records
15
+ def clean_revoked
16
+ table = @base_scope.arel_table
17
+
18
+ @base_scope.where.not(revoked_at: nil)
19
+ .where(table[:revoked_at].lt(Time.current))
20
+ .in_batches(&:delete_all)
21
+ end
22
+
23
+ # Clears expired records
24
+ def clean_expired(ttl)
25
+ table = @base_scope.arel_table
26
+
27
+ @base_scope.where(table[:created_at].lt(Time.current - ttl))
28
+ .in_batches(&:delete_all)
29
+ end
30
+ end
31
+ end
32
+ end
33
+ end
@@ -1,17 +1,27 @@
1
- require 'active_support/lazy_load_hooks'
1
+ # frozen_string_literal: true
2
+
3
+ require "active_support/lazy_load_hooks"
2
4
 
3
5
  module Doorkeeper
4
6
  module Orm
7
+ # ActiveRecord ORM for Doorkeeper entity models.
8
+ # Consists of three main OAuth entities:
9
+ # * Access Token
10
+ # * Access Grant
11
+ # * Application (client)
12
+ #
13
+ # Do a lazy loading of all the required and configured stuff.
14
+ #
5
15
  module ActiveRecord
6
16
  def self.initialize_models!
7
17
  lazy_load do
8
- require 'doorkeeper/orm/active_record/access_grant'
9
- require 'doorkeeper/orm/active_record/access_token'
10
- require 'doorkeeper/orm/active_record/application'
18
+ require "doorkeeper/orm/active_record/stale_records_cleaner"
19
+ require "doorkeeper/orm/active_record/access_grant"
20
+ require "doorkeeper/orm/active_record/access_token"
21
+ require "doorkeeper/orm/active_record/application"
11
22
 
12
- if Doorkeeper.configuration.active_record_options[:establish_connection]
13
- [Doorkeeper::AccessGrant, Doorkeeper::AccessToken, Doorkeeper::Application].each do |model|
14
- options = Doorkeeper.configuration.active_record_options[:establish_connection]
23
+ if (options = Doorkeeper.config.active_record_options[:establish_connection])
24
+ Doorkeeper::Orm::ActiveRecord.models.each do |model|
15
25
  model.establish_connection(options)
16
26
  end
17
27
  end
@@ -20,15 +30,23 @@ module Doorkeeper
20
30
 
21
31
  def self.initialize_application_owner!
22
32
  lazy_load do
23
- require 'doorkeeper/models/concerns/ownership'
33
+ require "doorkeeper/models/concerns/ownership"
24
34
 
25
- Doorkeeper::Application.send :include, Doorkeeper::Models::Ownership
35
+ Doorkeeper.config.application_model.include(Doorkeeper::Models::Ownership)
26
36
  end
27
37
  end
28
38
 
29
39
  def self.lazy_load(&block)
30
40
  ActiveSupport.on_load(:active_record, {}, &block)
31
41
  end
42
+
43
+ def self.models
44
+ [
45
+ Doorkeeper.config.access_grant_model,
46
+ Doorkeeper.config.access_token_model,
47
+ Doorkeeper.config.application_model,
48
+ ]
49
+ end
32
50
  end
33
51
  end
34
52
  end
@@ -1,12 +1,12 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Doorkeeper
2
4
  module Rails
3
5
  module Helpers
4
6
  def doorkeeper_authorize!(*scopes)
5
- @_doorkeeper_scopes = scopes.presence || Doorkeeper.configuration.default_scopes
7
+ @_doorkeeper_scopes = scopes.presence || Doorkeeper.config.default_scopes
6
8
 
7
- unless valid_doorkeeper_token?
8
- doorkeeper_render_error
9
- end
9
+ doorkeeper_render_error unless valid_doorkeeper_token?
10
10
  end
11
11
 
12
12
  def doorkeeper_unauthorized_render_options(**); end
@@ -14,13 +14,15 @@ module Doorkeeper
14
14
  def doorkeeper_forbidden_render_options(**); end
15
15
 
16
16
  def valid_doorkeeper_token?
17
- doorkeeper_token && doorkeeper_token.acceptable?(@_doorkeeper_scopes)
17
+ doorkeeper_token&.acceptable?(@_doorkeeper_scopes)
18
18
  end
19
19
 
20
20
  private
21
21
 
22
22
  def doorkeeper_render_error
23
23
  error = doorkeeper_error
24
+ error.raise_exception! if Doorkeeper.config.raise_on_errors?
25
+
24
26
  headers.merge!(error.headers.reject { |k| k == "Content-Type" })
25
27
  doorkeeper_render_error_with(error)
26
28
  end
@@ -28,7 +30,7 @@ module Doorkeeper
28
30
  def doorkeeper_render_error_with(error)
29
31
  options = doorkeeper_render_options(error) || {}
30
32
  status = doorkeeper_status_for_error(
31
- error, options.delete(:respond_not_found_when_forbidden)
33
+ error, options.delete(:respond_not_found_when_forbidden),
32
34
  )
33
35
  if options.blank?
34
36
  head status
@@ -68,9 +70,9 @@ module Doorkeeper
68
70
  end
69
71
 
70
72
  def doorkeeper_token
71
- @_doorkeeper_token ||= OAuth::Token.authenticate(
73
+ @doorkeeper_token ||= OAuth::Token.authenticate(
72
74
  request,
73
- *Doorkeeper.configuration.access_token_methods
75
+ *Doorkeeper.config.access_token_methods,
74
76
  )
75
77
  end
76
78
  end
@@ -0,0 +1,35 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Doorkeeper
4
+ module Rails
5
+ # Abstract router module that implements base behavior
6
+ # for generating and mapping Rails routes.
7
+ #
8
+ # Could be reused in Doorkeeper extensions.
9
+ #
10
+ module AbstractRouter
11
+ extend ActiveSupport::Concern
12
+
13
+ attr_reader :routes
14
+
15
+ def initialize(routes, mapper = Mapper.new, &block)
16
+ @routes = routes
17
+ @mapping = mapper.map(&block)
18
+ end
19
+
20
+ def generate_routes!(**_options)
21
+ raise NotImplementedError, "must be redefined for #{self.class.name}!"
22
+ end
23
+
24
+ private
25
+
26
+ def map_route(name, method)
27
+ return if @mapping.skipped?(name)
28
+
29
+ send(method, @mapping[name])
30
+
31
+ mapping[name] = @mapping[name]
32
+ end
33
+ end
34
+ end
35
+ end
@@ -1,9 +1,11 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Doorkeeper
2
4
  module Rails
3
5
  class Routes # :nodoc:
4
6
  class Mapper
5
- def initialize
6
- @mapping = Mapping.new
7
+ def initialize(mapping = Mapping.new)
8
+ @mapping = mapping
7
9
  end
8
10
 
9
11
  def map(&block)
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Doorkeeper
2
4
  module Rails
3
5
  class Routes # :nodoc:
@@ -6,17 +8,17 @@ module Doorkeeper
6
8
 
7
9
  def initialize
8
10
  @controllers = {
9
- authorizations: 'doorkeeper/authorizations',
10
- applications: 'doorkeeper/applications',
11
- authorized_applications: 'doorkeeper/authorized_applications',
12
- tokens: 'doorkeeper/tokens',
13
- token_info: 'doorkeeper/token_info'
11
+ authorizations: "doorkeeper/authorizations",
12
+ applications: "doorkeeper/applications",
13
+ authorized_applications: "doorkeeper/authorized_applications",
14
+ tokens: "doorkeeper/tokens",
15
+ token_info: "doorkeeper/token_info",
14
16
  }
15
17
 
16
18
  @as = {
17
19
  authorizations: :authorization,
18
20
  tokens: :token,
19
- token_info: :token_info
21
+ token_info: :token_info,
20
22
  }
21
23
 
22
24
  @skips = []
@@ -25,7 +27,7 @@ module Doorkeeper
25
27
  def [](routes)
26
28
  {
27
29
  controllers: @controllers[routes],
28
- as: @as[routes]
30
+ as: @as[routes],
29
31
  }
30
32
  end
31
33
 
@@ -0,0 +1,45 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Doorkeeper
4
+ module Rails
5
+ class Routes
6
+ # Thread-safe registry of any Doorkeeper additional routes.
7
+ # Used to allow implementing of Doorkeeper extensions that must
8
+ # use their own routes.
9
+ #
10
+ module Registry
11
+ ROUTES_ACCESS_LOCK = Mutex.new
12
+ ROUTES_DEFINITION_LOCK = Mutex.new
13
+
14
+ InvalidRouterClass = Class.new(StandardError)
15
+
16
+ # Collection of additional registered routes for Doorkeeper.
17
+ #
18
+ # @return [Array<Object>] set of registered routes
19
+ #
20
+ def registered_routes
21
+ ROUTES_DEFINITION_LOCK.synchronize do
22
+ @registered_routes ||= Set.new
23
+ end
24
+ end
25
+
26
+ # Registers additional routes in the Doorkeeper registry
27
+ #
28
+ # @param [Object] routes
29
+ # routes class
30
+ #
31
+ def register_routes(routes)
32
+ if !routes.is_a?(Module) || !(routes < AbstractRouter)
33
+ raise InvalidRouterClass, "routes class must include Doorkeeper::Rails::AbstractRouter"
34
+ end
35
+
36
+ ROUTES_ACCESS_LOCK.synchronize do
37
+ registered_routes << routes
38
+ end
39
+ end
40
+
41
+ alias register register_routes
42
+ end
43
+ end
44
+ end
45
+ end
@@ -1,5 +1,9 @@
1
- require 'doorkeeper/rails/routes/mapping'
2
- require 'doorkeeper/rails/routes/mapper'
1
+ # frozen_string_literal: true
2
+
3
+ require "doorkeeper/rails/routes/mapping"
4
+ require "doorkeeper/rails/routes/mapper"
5
+ require "doorkeeper/rails/routes/abstract_router"
6
+ require "doorkeeper/rails/routes/registry"
3
7
 
4
8
  module Doorkeeper
5
9
  module Rails
@@ -10,23 +14,29 @@ module Doorkeeper
10
14
  end
11
15
  end
12
16
 
13
- def self.install!
14
- ActionDispatch::Routing::Mapper.send :include, Doorkeeper::Rails::Routes::Helper
17
+ include AbstractRouter
18
+ extend Registry
19
+
20
+ mattr_reader :mapping do
21
+ {}
15
22
  end
16
23
 
17
- attr_reader :routes
24
+ def self.install!
25
+ ActionDispatch::Routing::Mapper.include Doorkeeper::Rails::Routes::Helper
26
+
27
+ registered_routes.each(&:install!)
28
+ end
18
29
 
19
- def initialize(routes, &block)
20
- @routes = routes
21
- @mapping = Mapper.new.map(&block)
30
+ def initialize(routes, mapper = Mapper.new, &block)
31
+ super
22
32
  end
23
33
 
24
34
  def generate_routes!(options)
25
- routes.scope options[:scope] || 'oauth', as: 'oauth' do
35
+ routes.scope options[:scope] || "oauth", as: "oauth" do
26
36
  map_route(:authorizations, :authorization_routes)
27
37
  map_route(:tokens, :token_routes)
28
38
  map_route(:tokens, :revoke_routes)
29
- map_route(:tokens, :introspect_routes)
39
+ map_route(:tokens, :introspect_routes) unless Doorkeeper.config.allow_token_introspection.is_a?(FalseClass)
30
40
  map_route(:applications, :application_routes)
31
41
  map_route(:authorized_applications, :authorized_applications_routes)
32
42
  map_route(:token_info, :token_info_routes)
@@ -35,59 +45,56 @@ module Doorkeeper
35
45
 
36
46
  private
37
47
 
38
- def map_route(name, method)
39
- send(method, @mapping[name]) unless @mapping.skipped?(name)
40
- end
41
-
42
48
  def authorization_routes(mapping)
43
49
  routes.resource(
44
50
  :authorization,
45
- path: 'authorize',
51
+ path: "authorize",
46
52
  only: %i[create destroy],
47
53
  as: mapping[:as],
48
- controller: mapping[:controllers]
54
+ controller: mapping[:controllers],
49
55
  ) do
50
- routes.get native_authorization_code_route, action: :show, on: :member
51
- routes.get '/', action: :new, on: :member
56
+ routes.get "/native", action: :show, on: :member
57
+ routes.get "/", action: :new, on: :member
52
58
  end
53
59
  end
54
60
 
55
61
  def token_routes(mapping)
56
62
  routes.resource(
57
63
  :token,
58
- path: 'token',
64
+ path: "token",
59
65
  only: [:create], as: mapping[:as],
60
- controller: mapping[:controllers]
66
+ controller: mapping[:controllers],
61
67
  )
62
68
  end
63
69
 
64
70
  def revoke_routes(mapping)
65
- routes.post 'revoke', controller: mapping[:controllers], action: :revoke
71
+ routes.post "revoke", controller: mapping[:controllers], action: :revoke
66
72
  end
67
73
 
68
74
  def introspect_routes(mapping)
69
- routes.post 'introspect', controller: mapping[:controllers], action: :introspect
75
+ routes.post "introspect", controller: mapping[:controllers], action: :introspect
70
76
  end
71
77
 
72
78
  def token_info_routes(mapping)
73
79
  routes.resource(
74
80
  :token_info,
75
- path: 'token/info',
81
+ path: "token/info",
76
82
  only: [:show], as: mapping[:as],
77
- controller: mapping[:controllers]
83
+ controller: mapping[:controllers],
78
84
  )
79
85
  end
80
86
 
81
87
  def application_routes(mapping)
82
- routes.resources :doorkeeper_applications, controller: mapping[:controllers], as: :applications, path: 'applications'
88
+ routes.resources :doorkeeper_applications,
89
+ controller: mapping[:controllers],
90
+ as: :applications,
91
+ path: "applications"
83
92
  end
84
93
 
85
94
  def authorized_applications_routes(mapping)
86
- routes.resources :authorized_applications, only: %i[index destroy], controller: mapping[:controllers]
87
- end
88
-
89
- def native_authorization_code_route
90
- Doorkeeper.configuration.native_authorization_code_route
95
+ routes.resources :authorized_applications,
96
+ only: %i[index destroy],
97
+ controller: mapping[:controllers]
91
98
  end
92
99
  end
93
100
  end