doorkeeper 5.0.3 → 5.1.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.
- checksums.yaml +4 -4
- data/.hound.yml +2 -1
- data/.rubocop.yml +37 -4
- data/.travis.yml +11 -21
- data/Appraisals +29 -7
- data/Dangerfile +5 -2
- data/Gemfile +19 -5
- data/NEWS.md +81 -21
- data/README.md +75 -485
- data/Rakefile +10 -8
- data/app/controllers/doorkeeper/application_controller.rb +1 -2
- data/app/controllers/doorkeeper/application_metal_controller.rb +2 -13
- data/app/controllers/doorkeeper/applications_controller.rb +20 -8
- data/app/controllers/doorkeeper/authorized_applications_controller.rb +1 -1
- data/app/controllers/doorkeeper/token_info_controller.rb +2 -2
- data/app/controllers/doorkeeper/tokens_controller.rb +11 -11
- data/app/helpers/doorkeeper/dashboard_helper.rb +1 -1
- data/app/validators/redirect_uri_validator.rb +5 -2
- data/app/views/doorkeeper/applications/_form.html.erb +6 -0
- data/app/views/doorkeeper/applications/show.html.erb +1 -1
- data/app/views/layouts/doorkeeper/admin.html.erb +5 -3
- data/bin/console +16 -0
- data/config/locales/en.yml +1 -0
- data/doorkeeper.gemspec +24 -21
- data/gemfiles/rails_5_0.gemfile +9 -4
- data/gemfiles/rails_5_1.gemfile +9 -4
- data/gemfiles/rails_5_2.gemfile +10 -5
- data/gemfiles/rails_6_0.gemfile +17 -0
- data/gemfiles/rails_master.gemfile +9 -9
- data/lib/doorkeeper/config/option.rb +64 -0
- data/lib/doorkeeper/config.rb +191 -75
- data/lib/doorkeeper/engine.rb +1 -1
- data/lib/doorkeeper/grape/authorization_decorator.rb +4 -4
- data/lib/doorkeeper/grape/helpers.rb +3 -3
- data/lib/doorkeeper/helpers/controller.rb +3 -2
- data/lib/doorkeeper/models/access_grant_mixin.rb +20 -3
- data/lib/doorkeeper/models/access_token_mixin.rb +63 -19
- data/lib/doorkeeper/models/application_mixin.rb +43 -1
- data/lib/doorkeeper/models/concerns/expirable.rb +4 -2
- data/lib/doorkeeper/models/concerns/ownership.rb +1 -6
- data/lib/doorkeeper/models/concerns/reusable.rb +19 -0
- data/lib/doorkeeper/models/concerns/revocable.rb +2 -1
- data/lib/doorkeeper/models/concerns/scopes.rb +5 -1
- data/lib/doorkeeper/models/concerns/secret_storable.rb +108 -0
- data/lib/doorkeeper/oauth/authorization/code.rb +2 -2
- data/lib/doorkeeper/oauth/authorization/token.rb +12 -7
- data/lib/doorkeeper/oauth/authorization/uri_builder.rb +1 -1
- data/lib/doorkeeper/oauth/authorization_code_request.rb +6 -4
- data/lib/doorkeeper/oauth/client.rb +1 -1
- data/lib/doorkeeper/oauth/client_credentials/validation.rb +5 -4
- data/lib/doorkeeper/oauth/client_credentials_request.rb +1 -1
- data/lib/doorkeeper/oauth/code_response.rb +2 -2
- data/lib/doorkeeper/oauth/error_response.rb +10 -6
- data/lib/doorkeeper/oauth/forbidden_token_response.rb +1 -1
- data/lib/doorkeeper/oauth/helpers/scope_checker.rb +23 -8
- data/lib/doorkeeper/oauth/helpers/unique_token.rb +13 -1
- data/lib/doorkeeper/oauth/helpers/uri_checker.rb +37 -1
- data/lib/doorkeeper/oauth/invalid_token_response.rb +5 -1
- data/lib/doorkeeper/oauth/password_access_token_request.rb +7 -2
- data/lib/doorkeeper/oauth/pre_authorization.rb +11 -5
- data/lib/doorkeeper/oauth/refresh_token_request.rb +5 -2
- data/lib/doorkeeper/oauth/scopes.rb +5 -3
- data/lib/doorkeeper/oauth/token.rb +2 -2
- data/lib/doorkeeper/oauth/token_introspection.rb +74 -8
- data/lib/doorkeeper/oauth/token_response.rb +9 -9
- data/lib/doorkeeper/oauth.rb +5 -5
- data/lib/doorkeeper/orm/active_record/access_grant.rb +27 -13
- data/lib/doorkeeper/orm/active_record/access_token.rb +6 -13
- data/lib/doorkeeper/orm/active_record/application.rb +21 -57
- data/lib/doorkeeper/orm/active_record/stale_records_cleaner.rb +10 -3
- data/lib/doorkeeper/orm/active_record.rb +6 -6
- data/lib/doorkeeper/rails/helpers.rb +1 -1
- data/lib/doorkeeper/rails/routes/mapping.rb +7 -7
- data/lib/doorkeeper/rails/routes.rb +11 -11
- data/lib/doorkeeper/rake/db.rake +13 -13
- data/lib/doorkeeper/rake.rb +1 -1
- data/lib/doorkeeper/request.rb +1 -1
- data/lib/doorkeeper/secret_storing/base.rb +64 -0
- data/lib/doorkeeper/secret_storing/bcrypt.rb +60 -0
- data/lib/doorkeeper/secret_storing/plain.rb +33 -0
- data/lib/doorkeeper/secret_storing/sha256_hash.rb +26 -0
- data/lib/doorkeeper/stale_records_cleaner.rb +1 -1
- data/lib/doorkeeper/version.rb +3 -3
- data/lib/doorkeeper.rb +69 -60
- data/lib/generators/doorkeeper/application_owner_generator.rb +10 -9
- data/lib/generators/doorkeeper/confidential_applications_generator.rb +10 -9
- data/lib/generators/doorkeeper/install_generator.rb +11 -9
- data/lib/generators/doorkeeper/migration_generator.rb +9 -9
- data/lib/generators/doorkeeper/pkce_generator.rb +10 -9
- data/lib/generators/doorkeeper/previous_refresh_token_generator.rb +10 -9
- data/lib/generators/doorkeeper/templates/initializer.rb +120 -13
- data/lib/generators/doorkeeper/templates/migration.rb.erb +15 -7
- data/lib/generators/doorkeeper/views_generator.rb +6 -4
- data/spec/controllers/application_metal_controller_spec.rb +24 -10
- data/spec/controllers/applications_controller_spec.rb +54 -52
- data/spec/controllers/authorizations_controller_spec.rb +139 -145
- data/spec/controllers/protected_resources_controller_spec.rb +78 -76
- data/spec/controllers/token_info_controller_spec.rb +14 -12
- data/spec/controllers/tokens_controller_spec.rb +167 -108
- data/spec/dummy/Rakefile +3 -1
- data/spec/dummy/app/controllers/application_controller.rb +3 -1
- data/spec/dummy/app/controllers/custom_authorizations_controller.rb +2 -0
- data/spec/dummy/app/controllers/full_protected_resources_controller.rb +4 -2
- data/spec/dummy/app/controllers/home_controller.rb +5 -3
- data/spec/dummy/app/controllers/metal_controller.rb +2 -0
- data/spec/dummy/app/controllers/semi_protected_resources_controller.rb +4 -2
- data/spec/dummy/app/helpers/application_helper.rb +2 -0
- data/spec/dummy/app/models/user.rb +2 -0
- data/spec/dummy/config/application.rb +25 -1
- data/spec/dummy/config/environments/development.rb +2 -0
- data/spec/dummy/config/environments/production.rb +2 -0
- data/spec/dummy/config/environments/test.rb +3 -1
- data/spec/dummy/config/initializers/backtrace_silencers.rb +2 -0
- data/spec/dummy/config/initializers/doorkeeper.rb +5 -2
- data/spec/dummy/config/initializers/secret_token.rb +3 -1
- data/spec/dummy/config/initializers/session_store.rb +3 -1
- data/spec/dummy/config/initializers/wrap_parameters.rb +2 -0
- data/spec/dummy/config.ru +3 -1
- data/spec/dummy/db/migrate/20151223192035_create_doorkeeper_tables.rb +17 -10
- data/spec/dummy/db/migrate/20170822064514_enable_pkce.rb +2 -0
- data/spec/dummy/db/schema.rb +1 -1
- data/spec/dummy/script/rails +5 -3
- data/spec/factories.rb +8 -6
- data/spec/generators/application_owner_generator_spec.rb +13 -26
- data/spec/generators/confidential_applications_generator_spec.rb +12 -28
- data/spec/generators/install_generator_spec.rb +17 -15
- data/spec/generators/migration_generator_spec.rb +13 -26
- data/spec/generators/pkce_generator_spec.rb +11 -26
- data/spec/generators/previous_refresh_token_generator_spec.rb +16 -29
- data/spec/generators/templates/routes.rb +2 -0
- data/spec/generators/views_generator_spec.rb +14 -12
- data/spec/grape/grape_integration_spec.rb +34 -32
- data/spec/helpers/doorkeeper/dashboard_helper_spec.rb +9 -7
- data/spec/lib/config_spec.rb +268 -99
- data/spec/lib/doorkeeper_spec.rb +3 -1
- data/spec/lib/models/expirable_spec.rb +22 -8
- data/spec/lib/models/reusable_spec.rb +40 -0
- data/spec/lib/models/revocable_spec.rb +8 -6
- data/spec/lib/models/scopes_spec.rb +27 -13
- data/spec/lib/models/secret_storable_spec.rb +135 -0
- data/spec/lib/oauth/authorization/uri_builder_spec.rb +17 -15
- data/spec/lib/oauth/authorization_code_request_spec.rb +34 -11
- data/spec/lib/oauth/base_request_spec.rb +20 -8
- data/spec/lib/oauth/base_response_spec.rb +3 -1
- data/spec/lib/oauth/client/credentials_spec.rb +24 -22
- data/spec/lib/oauth/client_credentials/creator_spec.rb +56 -10
- data/spec/lib/oauth/client_credentials/issuer_spec.rb +27 -18
- data/spec/lib/oauth/client_credentials/validation_spec.rb +20 -15
- data/spec/lib/oauth/client_credentials_integration_spec.rb +7 -5
- data/spec/lib/oauth/client_credentials_request_spec.rb +27 -21
- data/spec/lib/oauth/client_spec.rb +15 -13
- data/spec/lib/oauth/code_request_spec.rb +8 -6
- data/spec/lib/oauth/code_response_spec.rb +9 -7
- data/spec/lib/oauth/error_response_spec.rb +19 -11
- data/spec/lib/oauth/error_spec.rb +4 -2
- data/spec/lib/oauth/forbidden_token_response_spec.rb +7 -5
- data/spec/lib/oauth/helpers/scope_checker_spec.rb +68 -31
- data/spec/lib/oauth/helpers/unique_token_spec.rb +8 -6
- data/spec/lib/oauth/helpers/uri_checker_spec.rb +115 -95
- data/spec/lib/oauth/invalid_token_response_spec.rb +3 -1
- data/spec/lib/oauth/password_access_token_request_spec.rb +79 -30
- data/spec/lib/oauth/pre_authorization_spec.rb +80 -54
- data/spec/lib/oauth/refresh_token_request_spec.rb +36 -33
- data/spec/lib/oauth/scopes_spec.rb +63 -61
- data/spec/lib/oauth/token_request_spec.rb +79 -24
- data/spec/lib/oauth/token_response_spec.rb +40 -38
- data/spec/lib/oauth/token_spec.rb +60 -44
- data/spec/lib/request/strategy_spec.rb +3 -1
- data/spec/lib/secret_storing/base_spec.rb +60 -0
- data/spec/lib/secret_storing/bcrypt_spec.rb +49 -0
- data/spec/lib/secret_storing/plain_spec.rb +44 -0
- data/spec/lib/secret_storing/sha256_hash_spec.rb +48 -0
- data/spec/lib/server_spec.rb +16 -14
- data/spec/lib/stale_records_cleaner_spec.rb +17 -17
- data/spec/models/doorkeeper/access_grant_spec.rb +80 -15
- data/spec/models/doorkeeper/access_token_spec.rb +198 -73
- data/spec/models/doorkeeper/application_spec.rb +280 -288
- data/spec/requests/applications/applications_request_spec.rb +98 -66
- data/spec/requests/applications/authorized_applications_spec.rb +20 -18
- data/spec/requests/endpoints/authorization_spec.rb +25 -23
- data/spec/requests/endpoints/token_spec.rb +38 -36
- data/spec/requests/flows/authorization_code_errors_spec.rb +26 -24
- data/spec/requests/flows/authorization_code_spec.rb +193 -151
- data/spec/requests/flows/client_credentials_spec.rb +54 -52
- data/spec/requests/flows/implicit_grant_errors_spec.rb +10 -8
- data/spec/requests/flows/implicit_grant_spec.rb +27 -25
- data/spec/requests/flows/password_spec.rb +59 -55
- data/spec/requests/flows/refresh_token_spec.rb +45 -43
- data/spec/requests/flows/revoke_token_spec.rb +40 -54
- data/spec/requests/flows/skip_authorization_spec.rb +23 -21
- data/spec/requests/protected_resources/metal_spec.rb +7 -5
- data/spec/requests/protected_resources/private_api_spec.rb +35 -33
- data/spec/routing/custom_controller_routes_spec.rb +71 -65
- data/spec/routing/default_routes_spec.rb +22 -20
- data/spec/routing/scoped_routes_spec.rb +20 -18
- data/spec/spec_helper.rb +15 -13
- data/spec/spec_helper_integration.rb +3 -1
- data/spec/support/dependencies/factory_bot.rb +3 -1
- data/spec/support/doorkeeper_rspec.rb +3 -1
- data/spec/support/helpers/access_token_request_helper.rb +3 -1
- data/spec/support/helpers/authorization_request_helper.rb +4 -2
- data/spec/support/helpers/config_helper.rb +2 -0
- data/spec/support/helpers/model_helper.rb +3 -1
- data/spec/support/helpers/request_spec_helper.rb +5 -3
- data/spec/support/helpers/url_helper.rb +9 -7
- data/spec/support/http_method_shim.rb +4 -9
- data/spec/support/orm/active_record.rb +3 -1
- data/spec/support/shared/controllers_shared_context.rb +18 -16
- data/spec/support/shared/hashing_shared_context.rb +36 -0
- data/spec/support/shared/models_shared_examples.rb +12 -10
- data/spec/validators/redirect_uri_validator_spec.rb +74 -45
- data/spec/version/version_spec.rb +7 -5
- metadata +60 -26
- data/gemfiles/rails_4_2.gemfile +0 -13
- data/spec/dummy/config/initializers/new_framework_defaults.rb +0 -8
data/lib/doorkeeper/config.rb
CHANGED
|
@@ -1,9 +1,13 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "doorkeeper/config/option"
|
|
4
|
+
|
|
1
5
|
module Doorkeeper
|
|
2
6
|
class MissingConfiguration < StandardError
|
|
3
7
|
# Defines a MissingConfiguration error for a missing Doorkeeper
|
|
4
8
|
# configuration
|
|
5
9
|
def initialize
|
|
6
|
-
super(
|
|
10
|
+
super("Configuration for doorkeeper missing. Do you have doorkeeper initializer?")
|
|
7
11
|
end
|
|
8
12
|
end
|
|
9
13
|
|
|
@@ -12,6 +16,7 @@ module Doorkeeper
|
|
|
12
16
|
setup_orm_adapter
|
|
13
17
|
setup_orm_models
|
|
14
18
|
setup_application_owner if @config.enable_application_owner?
|
|
19
|
+
@config
|
|
15
20
|
end
|
|
16
21
|
|
|
17
22
|
def self.configuration
|
|
@@ -46,6 +51,7 @@ module Doorkeeper
|
|
|
46
51
|
end
|
|
47
52
|
|
|
48
53
|
def build
|
|
54
|
+
@config.validate
|
|
49
55
|
@config
|
|
50
56
|
end
|
|
51
57
|
|
|
@@ -83,6 +89,13 @@ module Doorkeeper
|
|
|
83
89
|
@config.instance_variable_set(:@optional_scopes, OAuth::Scopes.from_array(scopes))
|
|
84
90
|
end
|
|
85
91
|
|
|
92
|
+
# Define scopes_by_grant_type to limit certain scope to certain grant_type
|
|
93
|
+
# @param { Hash } with grant_types as keys.
|
|
94
|
+
# Default set to {} i.e. no limitation on scopes usage
|
|
95
|
+
def scopes_by_grant_type(hash = {})
|
|
96
|
+
@config.instance_variable_set(:@scopes_by_grant_type, hash)
|
|
97
|
+
end
|
|
98
|
+
|
|
86
99
|
# Change the way client credentials are retrieved from the request object.
|
|
87
100
|
# By default it retrieves first from the `HTTP_AUTHORIZATION` header, then
|
|
88
101
|
# falls back to the `:client_id` and `:client_secret` params from the
|
|
@@ -118,6 +131,15 @@ module Doorkeeper
|
|
|
118
131
|
@config.instance_variable_set(:@reuse_access_token, true)
|
|
119
132
|
end
|
|
120
133
|
|
|
134
|
+
# Sets the token_reuse_limit
|
|
135
|
+
# It will be used only when reuse_access_token option in enabled
|
|
136
|
+
# By default it will be 100
|
|
137
|
+
# It will be used for token reusablity to some threshold percentage
|
|
138
|
+
# Rationale: https://github.com/doorkeeper-gem/doorkeeper/issues/1189
|
|
139
|
+
def token_reuse_limit(percentage)
|
|
140
|
+
@config.instance_variable_set(:@token_reuse_limit, percentage)
|
|
141
|
+
end
|
|
142
|
+
|
|
121
143
|
# Use an API mode for applications generated with --api argument
|
|
122
144
|
# It will skip applications controller, disable forgery protection
|
|
123
145
|
def api_only
|
|
@@ -136,63 +158,54 @@ module Doorkeeper
|
|
|
136
158
|
def enforce_content_type
|
|
137
159
|
@config.instance_variable_set(:@enforce_content_type, true)
|
|
138
160
|
end
|
|
139
|
-
end
|
|
140
161
|
|
|
141
|
-
|
|
142
|
-
#
|
|
162
|
+
# Allow optional hashing of input tokens before persisting them.
|
|
163
|
+
# Will be used for hashing of input token and grants.
|
|
143
164
|
#
|
|
144
|
-
#
|
|
145
|
-
#
|
|
146
|
-
#
|
|
147
|
-
#
|
|
148
|
-
#
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
#
|
|
157
|
-
#
|
|
158
|
-
#
|
|
159
|
-
# * [:+as+] Set the builder method that goes inside +configure+ block
|
|
160
|
-
# * [+:default+] The default value in case no option was set
|
|
161
|
-
#
|
|
162
|
-
# ==== Examples
|
|
163
|
-
#
|
|
164
|
-
# option :name
|
|
165
|
-
# option :name, as: :set_name
|
|
166
|
-
# option :name, default: 'My Name'
|
|
167
|
-
# option :scopes builder_class: ScopesBuilder
|
|
165
|
+
# @param using
|
|
166
|
+
# Provide a different secret storage implementation class for tokens
|
|
167
|
+
# @param fallback
|
|
168
|
+
# Provide a fallback secret storage implementation class for tokens
|
|
169
|
+
# or use :plain to fallback to plain tokens
|
|
170
|
+
def hash_token_secrets(using: nil, fallback: nil)
|
|
171
|
+
default = "::Doorkeeper::SecretStoring::Sha256Hash"
|
|
172
|
+
configure_secrets_for :token,
|
|
173
|
+
using: using || default,
|
|
174
|
+
fallback: fallback
|
|
175
|
+
end
|
|
176
|
+
|
|
177
|
+
# Allow optional hashing of application secrets before persisting them.
|
|
178
|
+
# Will be used for hashing of input token and grants.
|
|
168
179
|
#
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
@config.instance_variable_set(:"@#{attribute}", value)
|
|
184
|
-
end
|
|
185
|
-
end
|
|
180
|
+
# @param using
|
|
181
|
+
# Provide a different secret storage implementation for applications
|
|
182
|
+
# @param fallback
|
|
183
|
+
# Provide a fallback secret storage implementation for applications
|
|
184
|
+
# or use :plain to fallback to plain application secrets
|
|
185
|
+
def hash_application_secrets(using: nil, fallback: nil)
|
|
186
|
+
default = "::Doorkeeper::SecretStoring::Sha256Hash"
|
|
187
|
+
configure_secrets_for :application,
|
|
188
|
+
using: using || default,
|
|
189
|
+
fallback: fallback
|
|
190
|
+
end
|
|
191
|
+
|
|
192
|
+
private
|
|
186
193
|
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
194
|
+
# Configure the secret storing functionality
|
|
195
|
+
def configure_secrets_for(type, using:, fallback:)
|
|
196
|
+
raise ArgumentError, "Invalid type #{type}" if %i[application token].exclude?(type)
|
|
197
|
+
|
|
198
|
+
@config.instance_variable_set(:"@#{type}_secret_strategy",
|
|
199
|
+
using.constantize)
|
|
200
|
+
|
|
201
|
+
if fallback.nil?
|
|
202
|
+
return
|
|
203
|
+
elsif fallback.to_sym == :plain
|
|
204
|
+
fallback = "::Doorkeeper::SecretStoring::Plain"
|
|
193
205
|
end
|
|
194
206
|
|
|
195
|
-
|
|
207
|
+
@config.instance_variable_set(:"@#{type}_secret_fallback_strategy",
|
|
208
|
+
fallback.constantize)
|
|
196
209
|
end
|
|
197
210
|
end
|
|
198
211
|
|
|
@@ -202,7 +215,7 @@ module Doorkeeper
|
|
|
202
215
|
as: :authenticate_resource_owner,
|
|
203
216
|
default: (lambda do |_routes|
|
|
204
217
|
::Rails.logger.warn(
|
|
205
|
-
I18n.t(
|
|
218
|
+
I18n.t("doorkeeper.errors.messages.resource_owner_authenticator_not_configured")
|
|
206
219
|
)
|
|
207
220
|
|
|
208
221
|
nil
|
|
@@ -212,7 +225,7 @@ module Doorkeeper
|
|
|
212
225
|
as: :authenticate_admin,
|
|
213
226
|
default: (lambda do |_routes|
|
|
214
227
|
::Rails.logger.warn(
|
|
215
|
-
I18n.t(
|
|
228
|
+
I18n.t("doorkeeper.errors.messages.admin_authenticator_not_configured")
|
|
216
229
|
)
|
|
217
230
|
|
|
218
231
|
head :forbidden
|
|
@@ -221,22 +234,27 @@ module Doorkeeper
|
|
|
221
234
|
option :resource_owner_from_credentials,
|
|
222
235
|
default: (lambda do |_routes|
|
|
223
236
|
::Rails.logger.warn(
|
|
224
|
-
I18n.t(
|
|
237
|
+
I18n.t("doorkeeper.errors.messages.credential_flow_not_configured")
|
|
225
238
|
)
|
|
226
239
|
|
|
227
240
|
nil
|
|
228
241
|
end)
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
option :
|
|
232
|
-
option :
|
|
233
|
-
|
|
242
|
+
|
|
243
|
+
# Hooks for authorization
|
|
244
|
+
option :before_successful_authorization, default: ->(_context) {}
|
|
245
|
+
option :after_successful_authorization, default: ->(_context) {}
|
|
246
|
+
# Hooks for strategies responses
|
|
247
|
+
option :before_successful_strategy_response, default: ->(_request) {}
|
|
248
|
+
option :after_successful_strategy_response, default: ->(_request, _response) {}
|
|
249
|
+
# Allows to customize Token Introspection response
|
|
250
|
+
option :custom_introspection_response, default: ->(_token, _context) { {} }
|
|
251
|
+
|
|
234
252
|
option :skip_authorization, default: ->(_routes) {}
|
|
235
253
|
option :access_token_expires_in, default: 7200
|
|
236
254
|
option :custom_access_token_expires_in, default: ->(_context) { nil }
|
|
237
255
|
option :authorization_code_expires_in, default: 600
|
|
238
256
|
option :orm, default: :active_record
|
|
239
|
-
option :native_redirect_uri, default:
|
|
257
|
+
option :native_redirect_uri, default: "urn:ietf:wg:oauth:2.0:oob"
|
|
240
258
|
option :active_record_options, default: {}
|
|
241
259
|
option :grant_flows, default: %w[authorization_code client_credentials]
|
|
242
260
|
option :handle_auth_errors, default: :render
|
|
@@ -252,7 +270,7 @@ module Doorkeeper
|
|
|
252
270
|
#
|
|
253
271
|
# @param realm [String] ("Doorkeeper") Authentication realm
|
|
254
272
|
#
|
|
255
|
-
option :realm, default:
|
|
273
|
+
option :realm, default: "Doorkeeper"
|
|
256
274
|
|
|
257
275
|
# Forces the usage of the HTTPS protocol in non-native redirect uris
|
|
258
276
|
# (enabled by default in non-development environments). OAuth2
|
|
@@ -276,7 +294,15 @@ module Doorkeeper
|
|
|
276
294
|
# the name of the access token generator class
|
|
277
295
|
#
|
|
278
296
|
option :access_token_generator,
|
|
279
|
-
default:
|
|
297
|
+
default: "Doorkeeper::OAuth::Helpers::UniqueToken"
|
|
298
|
+
|
|
299
|
+
# Default access token generator is a SecureRandom class from Ruby stdlib.
|
|
300
|
+
# This option defines which method will be used to generate a unique token value.
|
|
301
|
+
#
|
|
302
|
+
# @param access_token_generator [String]
|
|
303
|
+
# the name of the access token generator class
|
|
304
|
+
#
|
|
305
|
+
option :default_generator_method, default: :urlsafe_base64
|
|
280
306
|
|
|
281
307
|
# The controller Doorkeeper::ApplicationController inherits from.
|
|
282
308
|
# Defaults to ActionController::Base.
|
|
@@ -284,11 +310,29 @@ module Doorkeeper
|
|
|
284
310
|
#
|
|
285
311
|
# @param base_controller [String] the name of the base controller
|
|
286
312
|
option :base_controller,
|
|
287
|
-
default:
|
|
313
|
+
default: "ActionController::Base"
|
|
288
314
|
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
315
|
+
# Allows to set blank redirect URIs for Applications in case
|
|
316
|
+
# server configured to use URI-less grant flows.
|
|
317
|
+
#
|
|
318
|
+
option :allow_blank_redirect_uri,
|
|
319
|
+
default: (lambda do |grant_flows, _application|
|
|
320
|
+
grant_flows.exclude?("authorization_code") &&
|
|
321
|
+
grant_flows.exclude?("implicit")
|
|
322
|
+
end)
|
|
323
|
+
|
|
324
|
+
attr_reader :api_only,
|
|
325
|
+
:enforce_content_type,
|
|
326
|
+
:reuse_access_token,
|
|
327
|
+
:token_secret_fallback_strategy,
|
|
328
|
+
:application_secret_fallback_strategy
|
|
329
|
+
|
|
330
|
+
# Return the valid subset of this configuration
|
|
331
|
+
def validate
|
|
332
|
+
validate_reuse_access_token_value
|
|
333
|
+
validate_token_reuse_limit
|
|
334
|
+
validate_secret_strategies
|
|
335
|
+
end
|
|
292
336
|
|
|
293
337
|
def api_only
|
|
294
338
|
@api_only ||= false
|
|
@@ -306,22 +350,34 @@ module Doorkeeper
|
|
|
306
350
|
end
|
|
307
351
|
end
|
|
308
352
|
|
|
353
|
+
def token_reuse_limit
|
|
354
|
+
@token_reuse_limit ||= 100
|
|
355
|
+
end
|
|
356
|
+
|
|
309
357
|
def enforce_configured_scopes?
|
|
310
|
-
|
|
358
|
+
option_set? :enforce_configured_scopes
|
|
311
359
|
end
|
|
312
360
|
|
|
313
361
|
def enable_application_owner?
|
|
314
|
-
|
|
362
|
+
option_set? :enable_application_owner
|
|
315
363
|
end
|
|
316
364
|
|
|
317
365
|
def confirm_application_owner?
|
|
318
|
-
|
|
366
|
+
option_set? :confirm_application_owner
|
|
319
367
|
end
|
|
320
368
|
|
|
321
369
|
def raise_on_errors?
|
|
322
370
|
handle_auth_errors == :raise
|
|
323
371
|
end
|
|
324
372
|
|
|
373
|
+
def token_secret_strategy
|
|
374
|
+
@token_secret_strategy ||= ::Doorkeeper::SecretStoring::Plain
|
|
375
|
+
end
|
|
376
|
+
|
|
377
|
+
def application_secret_strategy
|
|
378
|
+
@application_secret_strategy ||= ::Doorkeeper::SecretStoring::Plain
|
|
379
|
+
end
|
|
380
|
+
|
|
325
381
|
def default_scopes
|
|
326
382
|
@default_scopes ||= OAuth::Scopes.new
|
|
327
383
|
end
|
|
@@ -334,12 +390,20 @@ module Doorkeeper
|
|
|
334
390
|
@scopes ||= default_scopes + optional_scopes
|
|
335
391
|
end
|
|
336
392
|
|
|
393
|
+
def scopes_by_grant_type
|
|
394
|
+
@scopes_by_grant_type ||= {}
|
|
395
|
+
end
|
|
396
|
+
|
|
337
397
|
def client_credentials_methods
|
|
338
398
|
@client_credentials_methods ||= %i[from_basic from_params]
|
|
339
399
|
end
|
|
340
400
|
|
|
341
401
|
def access_token_methods
|
|
342
|
-
@access_token_methods ||= %i[
|
|
402
|
+
@access_token_methods ||= %i[
|
|
403
|
+
from_bearer_authorization
|
|
404
|
+
from_access_token_param
|
|
405
|
+
from_bearer_param
|
|
406
|
+
]
|
|
343
407
|
end
|
|
344
408
|
|
|
345
409
|
def authorization_response_types
|
|
@@ -350,15 +414,33 @@ module Doorkeeper
|
|
|
350
414
|
@token_grant_types ||= calculate_token_grant_types.freeze
|
|
351
415
|
end
|
|
352
416
|
|
|
417
|
+
def allow_blank_redirect_uri?(application = nil)
|
|
418
|
+
if allow_blank_redirect_uri.respond_to?(:call)
|
|
419
|
+
allow_blank_redirect_uri.call(grant_flows, application)
|
|
420
|
+
else
|
|
421
|
+
allow_blank_redirect_uri
|
|
422
|
+
end
|
|
423
|
+
end
|
|
424
|
+
|
|
425
|
+
def option_defined?(name)
|
|
426
|
+
instance_variable_defined?("@#{name}")
|
|
427
|
+
end
|
|
428
|
+
|
|
353
429
|
private
|
|
354
430
|
|
|
431
|
+
# Helper to read boolearized configuration option
|
|
432
|
+
def option_set?(instance_key)
|
|
433
|
+
var = instance_variable_get("@#{instance_key}")
|
|
434
|
+
!!(defined?(var) && var)
|
|
435
|
+
end
|
|
436
|
+
|
|
355
437
|
# Determines what values are acceptable for 'response_type' param in
|
|
356
438
|
# authorization request endpoint, and return them as an array of strings.
|
|
357
439
|
#
|
|
358
440
|
def calculate_authorization_response_types
|
|
359
441
|
types = []
|
|
360
|
-
types <<
|
|
361
|
-
types <<
|
|
442
|
+
types << "code" if grant_flows.include? "authorization_code"
|
|
443
|
+
types << "token" if grant_flows.include? "implicit"
|
|
362
444
|
types
|
|
363
445
|
end
|
|
364
446
|
|
|
@@ -366,9 +448,43 @@ module Doorkeeper
|
|
|
366
448
|
# request endpoint, and return them in array.
|
|
367
449
|
#
|
|
368
450
|
def calculate_token_grant_types
|
|
369
|
-
types = grant_flows - [
|
|
370
|
-
types <<
|
|
451
|
+
types = grant_flows - ["implicit"]
|
|
452
|
+
types << "refresh_token" if refresh_token_enabled?
|
|
371
453
|
types
|
|
372
454
|
end
|
|
455
|
+
|
|
456
|
+
# Determine whether +reuse_access_token+ and a non-restorable
|
|
457
|
+
# +token_secret_strategy+ have both been activated.
|
|
458
|
+
#
|
|
459
|
+
# In that case, disable reuse_access_token value and warn the user.
|
|
460
|
+
def validate_reuse_access_token_value
|
|
461
|
+
strategy = token_secret_strategy
|
|
462
|
+
return if !reuse_access_token || strategy.allows_restoring_secrets?
|
|
463
|
+
|
|
464
|
+
::Rails.logger.warn(
|
|
465
|
+
"You have configured both reuse_access_token " \
|
|
466
|
+
"AND strategy strategy '#{strategy}' that cannot restore tokens. " \
|
|
467
|
+
"This combination is unsupported. reuse_access_token will be disabled"
|
|
468
|
+
)
|
|
469
|
+
@reuse_access_token = false
|
|
470
|
+
end
|
|
471
|
+
|
|
472
|
+
# Validate that the provided strategies are valid for
|
|
473
|
+
# tokens and applications
|
|
474
|
+
def validate_secret_strategies
|
|
475
|
+
token_secret_strategy.validate_for :token
|
|
476
|
+
application_secret_strategy.validate_for :application
|
|
477
|
+
end
|
|
478
|
+
|
|
479
|
+
def validate_token_reuse_limit
|
|
480
|
+
return if !reuse_access_token ||
|
|
481
|
+
(token_reuse_limit > 0 && token_reuse_limit <= 100)
|
|
482
|
+
|
|
483
|
+
::Rails.logger.warn(
|
|
484
|
+
"You have configured an invalid value for token_reuse_limit option. " \
|
|
485
|
+
"It will be set to default 100"
|
|
486
|
+
)
|
|
487
|
+
@token_reuse_limit = 100
|
|
488
|
+
end
|
|
373
489
|
end
|
|
374
490
|
end
|
data/lib/doorkeeper/engine.rb
CHANGED
|
@@ -18,7 +18,7 @@ module Doorkeeper
|
|
|
18
18
|
end
|
|
19
19
|
|
|
20
20
|
if defined?(Sprockets) && Sprockets::VERSION.chr.to_i >= 4
|
|
21
|
-
initializer
|
|
21
|
+
initializer "doorkeeper.assets.precompile" do |app|
|
|
22
22
|
# Force users to use:
|
|
23
23
|
# //= link doorkeeper/admin/application.css
|
|
24
24
|
# in Doorkeeper 5 for Sprockets 4 instead of precompile.
|
|
@@ -9,10 +9,10 @@ module Doorkeeper
|
|
|
9
9
|
|
|
10
10
|
def authorization
|
|
11
11
|
env = __getobj__.env
|
|
12
|
-
env[
|
|
13
|
-
env[
|
|
14
|
-
env[
|
|
15
|
-
env[
|
|
12
|
+
env["HTTP_AUTHORIZATION"] ||
|
|
13
|
+
env["X-HTTP_AUTHORIZATION"] ||
|
|
14
|
+
env["X_HTTP_AUTHORIZATION"] ||
|
|
15
|
+
env["REDIRECT_X_HTTP_AUTHORIZATION"]
|
|
16
16
|
end
|
|
17
17
|
end
|
|
18
18
|
end
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
|
-
require
|
|
3
|
+
require "doorkeeper/grape/authorization_decorator"
|
|
4
4
|
|
|
5
5
|
module Doorkeeper
|
|
6
6
|
module Grape
|
|
@@ -29,7 +29,7 @@ module Doorkeeper
|
|
|
29
29
|
private
|
|
30
30
|
|
|
31
31
|
def endpoint
|
|
32
|
-
env[
|
|
32
|
+
env["api.endpoint"]
|
|
33
33
|
end
|
|
34
34
|
|
|
35
35
|
def doorkeeper_token
|
|
@@ -46,7 +46,7 @@ module Doorkeeper
|
|
|
46
46
|
def error_status_codes
|
|
47
47
|
{
|
|
48
48
|
unauthorized: 401,
|
|
49
|
-
forbidden: 403
|
|
49
|
+
forbidden: 403,
|
|
50
50
|
}
|
|
51
51
|
end
|
|
52
52
|
end
|
|
@@ -55,8 +55,9 @@ module Doorkeeper
|
|
|
55
55
|
end
|
|
56
56
|
|
|
57
57
|
def enforce_content_type
|
|
58
|
-
|
|
59
|
-
|
|
58
|
+
if (request.put? || request.post? || request.patch?) && request.content_type != "application/x-www-form-urlencoded"
|
|
59
|
+
render json: {}, status: :unsupported_media_type
|
|
60
|
+
end
|
|
60
61
|
end
|
|
61
62
|
end
|
|
62
63
|
end
|
|
@@ -9,6 +9,7 @@ module Doorkeeper
|
|
|
9
9
|
include Models::Revocable
|
|
10
10
|
include Models::Accessible
|
|
11
11
|
include Models::Orderable
|
|
12
|
+
include Models::SecretStorable
|
|
12
13
|
include Models::Scopes
|
|
13
14
|
|
|
14
15
|
# never uses pkce, if pkce migrations were not generated
|
|
@@ -30,7 +31,7 @@ module Doorkeeper
|
|
|
30
31
|
# if there is no record with such token
|
|
31
32
|
#
|
|
32
33
|
def by_token(token)
|
|
33
|
-
|
|
34
|
+
find_by_plaintext_token(:token, token)
|
|
34
35
|
end
|
|
35
36
|
|
|
36
37
|
# Revokes AccessGrant records that have not been revoked and associated
|
|
@@ -85,15 +86,31 @@ module Doorkeeper
|
|
|
85
86
|
|
|
86
87
|
# @param code_verifier [#to_s] a one time use value (any object that responds to `#to_s`)
|
|
87
88
|
#
|
|
88
|
-
# @return [#to_s] An encoded code challenge based on the provided verifier
|
|
89
|
+
# @return [#to_s] An encoded code challenge based on the provided verifier
|
|
90
|
+
# suitable for PKCE validation
|
|
91
|
+
#
|
|
89
92
|
def generate_code_challenge(code_verifier)
|
|
90
93
|
padded_result = Base64.urlsafe_encode64(Digest::SHA256.digest(code_verifier))
|
|
91
|
-
padded_result.split(
|
|
94
|
+
padded_result.split("=")[0] # Remove any trailing '='
|
|
92
95
|
end
|
|
93
96
|
|
|
94
97
|
def pkce_supported?
|
|
95
98
|
new.pkce_supported?
|
|
96
99
|
end
|
|
100
|
+
|
|
101
|
+
##
|
|
102
|
+
# Determines the secret storing transformer
|
|
103
|
+
# Unless configured otherwise, uses the plain secret strategy
|
|
104
|
+
def secret_strategy
|
|
105
|
+
::Doorkeeper.configuration.token_secret_strategy
|
|
106
|
+
end
|
|
107
|
+
|
|
108
|
+
##
|
|
109
|
+
# Determine the fallback storing strategy
|
|
110
|
+
# Unless configured, there will be no fallback
|
|
111
|
+
def fallback_secret_strategy
|
|
112
|
+
::Doorkeeper.configuration.token_secret_fallback_strategy
|
|
113
|
+
end
|
|
97
114
|
end
|
|
98
115
|
end
|
|
99
116
|
end
|