doorkeeper-openid_connect 1.7.2 → 1.7.3

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: dd500337bf3593b1f15ab64da67dd2da940797271fd1a169e47f2542371d6930
4
- data.tar.gz: 4c3fdae9aca104f74f2bcf2e2805d09fe784e75326e3fa2382de8ba74133987a
3
+ metadata.gz: ab0de01b3be4241280fd4846f9c38b4c915685918a6401e464dce609fb588ace
4
+ data.tar.gz: 999e38663483020d9c84b525f38842e0d9a5811c72ddfd04bdb7c86e1e018b2a
5
5
  SHA512:
6
- metadata.gz: 887f767a61bd22be260dfb2b3d37de2e3334b25ff53aacbf9b6b41aecb88a287ae308d9fd65950e7c850ab023569d08cb1c31cceda4182cb667c3b61a984406e
7
- data.tar.gz: 670454a6c3e5dbe69dcb511e68acbb63b2b558410a3ae0268400918dd11e3ae4d320fb1bd7d876cade2b7313132c925befcd51ad0bd023bfb826f36ee9d127b9
6
+ metadata.gz: '09f0860be72310e44989febad8997e4fce1a82bf8d2986cfa3dfe56a0c9e55414d74f19a6dae35636aa5871c5778baad7b8776627835a30bd356bbb251fc4e32'
7
+ data.tar.gz: d6d42d010bd3e216dd1f1c84d60f86b4944f43a64d48db2cd613fddb189c7ac6ef079b713a86dd0b95a3551756b15a4868287c1af836fc0ada87efc6e1efc630
@@ -1,5 +1,15 @@
1
1
  ## Unreleased
2
2
 
3
+ ## v1.7.3 (2020-07-06)
4
+
5
+ - [#111] Add configuration callback `select_account_for_resource_owner` to support the `prompt=select_account` param
6
+ - [#112] Add grant_types_supported to discovery response
7
+ - [#114] Fix user_info endpoint when used in api mode
8
+ - [#116] Support Doorkeeper API (> 5.4) for registering custom grant flows.
9
+ - [#117] Fix migration template to use Rails migrations DSL for association.
10
+ - [#118] Use fragment urls for implicit flow error redirects (thanks to @joeljunstrom)
11
+ - [#119] Execute end_session_endpoint in the controllers context (thanks to @joeljunstrom)
12
+
3
13
  ## v1.7.2 (2020-05-20)
4
14
 
5
15
  ### Changes
data/README.md CHANGED
@@ -139,6 +139,10 @@ The following settings are optional, but recommended for better client compatibi
139
139
  - Defines how to trigger reauthentication for the current user (e.g. display a password prompt, or sign-out the user and redirect to the login form).
140
140
  - Required to support the `max_age` and `prompt=login` parameters.
141
141
  - The block is executed in the controller's scope, so you have access to methods like `params`, `redirect_to` etc.
142
+ - `select_account_for_resource_owner`
143
+ - Defines how to trigger account selection to choose the current login user.
144
+ - Required to support the `prompt=select_account` parameter.
145
+ - The block is executed in the controller's scope, so you have access to methods like `params`, `redirect_to` etc.
142
146
 
143
147
  The following settings are optional:
144
148
 
@@ -155,6 +159,7 @@ The following settings are optional:
155
159
  - `end_session_endpoint`
156
160
  - The URL that the user is redirected to after ending the session on the client.
157
161
  - Used by implementations like https://github.com/IdentityModel/oidc-client-js.
162
+ - The block is executed in the controller's scope, so you have access to your route helpers.
158
163
 
159
164
  ### Scopes
160
165
 
@@ -38,16 +38,13 @@ module Doorkeeper
38
38
 
39
39
  # TODO: support id_token response type
40
40
  response_types_supported: doorkeeper.authorization_response_types,
41
- response_modes_supported: ['query', 'fragment'],
41
+ response_modes_supported: %w[query fragment],
42
+ grant_types_supported: grant_types_supported(doorkeeper),
42
43
 
43
- token_endpoint_auth_methods_supported: [
44
- 'client_secret_basic',
45
- 'client_secret_post',
46
-
47
- # TODO: look into doorkeeper-jwt_assertion for these
48
- # 'client_secret_jwt',
49
- # 'private_key_jwt'
50
- ],
44
+ # TODO: look into doorkeeper-jwt_assertion for these
45
+ # 'client_secret_jwt',
46
+ # 'private_key_jwt'
47
+ token_endpoint_auth_methods_supported: %w[client_secret_basic client_secret_post],
51
48
 
52
49
  subject_types_supported: openid_connect.subject_types_supported,
53
50
 
@@ -73,6 +70,12 @@ module Doorkeeper
73
70
  }.compact
74
71
  end
75
72
 
73
+ def grant_types_supported(doorkeeper)
74
+ grant_types_supported = doorkeeper.grant_flows
75
+ grant_types_supported << 'refresh_token' if doorkeeper.refresh_token_enabled?
76
+ grant_types_supported
77
+ end
78
+
76
79
  def webfinger_response
77
80
  {
78
81
  subject: params.require(:resource),
@@ -3,7 +3,9 @@
3
3
  module Doorkeeper
4
4
  module OpenidConnect
5
5
  class UserinfoController < ::Doorkeeper::ApplicationController
6
- skip_before_action :verify_authenticity_token
6
+ unless Doorkeeper.config.api_only
7
+ skip_before_action :verify_authenticity_token
8
+ end
7
9
  before_action -> { doorkeeper_authorize! :openid }
8
10
 
9
11
  def show
@@ -19,4 +19,5 @@ en:
19
19
  resource_owner_from_access_token_not_configured: 'Failure due to Doorkeeper::OpenidConnect.configure.resource_owner_from_access_token missing configuration.'
20
20
  auth_time_from_resource_owner_not_configured: 'Failure due to Doorkeeper::OpenidConnect.configure.auth_time_from_resource_owner missing configuration.'
21
21
  reauthenticate_resource_owner_not_configured: 'Failure due to Doorkeeper::OpenidConnect.configure.reauthenticate_resource_owner missing configuration.'
22
+ select_account_for_resource_owner_not_configured: 'Failure due to Doorkeeper::OpenidConnect.configure.select_account_for_resource_owner missing configuration.'
22
23
  subject_not_configured: 'ID Token generation failed due to Doorkeeper::OpenidConnect.configure.subject missing configuration.'
@@ -22,6 +22,7 @@ require 'doorkeeper/openid_connect/errors'
22
22
  require 'doorkeeper/openid_connect/id_token'
23
23
  require 'doorkeeper/openid_connect/id_token_token'
24
24
  require 'doorkeeper/openid_connect/user_info'
25
+ require 'doorkeeper/openid_connect/response_mode'
25
26
  require 'doorkeeper/openid_connect/version'
26
27
 
27
28
  require 'doorkeeper/openid_connect/helpers/controller'
@@ -63,5 +64,27 @@ module Doorkeeper
63
64
  key.slice(:kty, :kid)
64
65
  end
65
66
  end
67
+
68
+ if defined?(::Doorkeeper::GrantFlow)
69
+ Doorkeeper::GrantFlow.register(
70
+ :id_token,
71
+ response_type_matches: 'id_token',
72
+ response_type_strategy: Doorkeeper::OpenidConnect::IdToken,
73
+ )
74
+
75
+ Doorkeeper::GrantFlow.register(
76
+ 'id_token token',
77
+ response_type_matches: 'id_token token',
78
+ response_type_strategy: Doorkeeper::OpenidConnect::IdTokenToken,
79
+ )
80
+
81
+ Doorkeeper::GrantFlow.register_alias(
82
+ 'implicit_oidc', as: ['implicit', 'id_token', 'id_token token']
83
+ )
84
+ else
85
+ # TODO: drop this and corresponding file when we will set minimal
86
+ # required Doorkeeper version to 5.5.
87
+ Doorkeeper::Config.prepend OpenidConnect::ResponseTypeConfig
88
+ end
66
89
  end
67
90
  end
@@ -115,6 +115,10 @@ module Doorkeeper
115
115
  raise Errors::InvalidConfiguration, I18n.translate('doorkeeper.openid_connect.errors.messages.reauthenticate_resource_owner_not_configured')
116
116
  }
117
117
 
118
+ option :select_account_for_resource_owner, default: lambda { |*_|
119
+ raise Errors::InvalidConfiguration, I18n.translate('doorkeeper.openid_connect.errors.messages.select_account_for_resource_owner_not_configured')
120
+ }
121
+
118
122
  option :subject, default: lambda { |*_|
119
123
  raise Errors::InvalidConfiguration, I18n.translate('doorkeeper.openid_connect.errors.messages.subject_not_configured')
120
124
  }
@@ -26,7 +26,6 @@ module Doorkeeper
26
26
  class LoginRequired < OpenidConnectError; end
27
27
  class ConsentRequired < OpenidConnectError; end
28
28
  class InteractionRequired < OpenidConnectError; end
29
- class AccountSelectionRequired < OpenidConnectError; end
30
29
  end
31
30
  end
32
31
  end
@@ -43,12 +43,14 @@ module Doorkeeper
43
43
  name: exception.type,
44
44
  state: params[:state],
45
45
  redirect_uri: params[:redirect_uri],
46
+ response_on_fragment: pre_auth.response_on_fragment?,
46
47
  )
47
48
  else
48
49
  ::Doorkeeper::OAuth::ErrorResponse.new(
49
50
  name: exception.type,
50
51
  state: params[:state],
51
52
  redirect_uri: params[:redirect_uri],
53
+ response_on_fragment: pre_auth.response_on_fragment?,
52
54
  )
53
55
  end
54
56
 
@@ -75,8 +77,7 @@ module Doorkeeper
75
77
  when 'consent'
76
78
  render :new
77
79
  when 'select_account'
78
- # TODO: let the user implement this
79
- raise Errors::AccountSelectionRequired
80
+ select_account_for_oidc_resource_owner(owner)
80
81
  else
81
82
  raise Errors::InvalidRequest
82
83
  end
@@ -97,16 +98,21 @@ module Doorkeeper
97
98
  end
98
99
  end
99
100
 
100
- def reauthenticate_oidc_resource_owner(owner)
101
+ def return_without_oidc_prompt_param(prompt_value)
101
102
  return_to = URI.parse(request.path)
102
103
  return_to.query = request.query_parameters.tap do |params|
103
- params['prompt'] = params['prompt'].to_s.sub(/\blogin\s*\b/, '').strip
104
+ params['prompt'] = params['prompt'].to_s.sub(/\b#{prompt_value}\s*\b/, '').strip
104
105
  params.delete('prompt') if params['prompt'].blank?
105
106
  end.to_query
107
+ return_to.to_s
108
+ end
109
+
110
+ def reauthenticate_oidc_resource_owner(owner)
111
+ return_to = return_without_oidc_prompt_param('login')
106
112
 
107
113
  instance_exec(
108
114
  owner,
109
- return_to.to_s,
115
+ return_to,
110
116
  &Doorkeeper::OpenidConnect.configuration.reauthenticate_resource_owner
111
117
  )
112
118
 
@@ -116,6 +122,16 @@ module Doorkeeper
116
122
  def oidc_consent_required?
117
123
  !skip_authorization? && !matching_token?
118
124
  end
125
+
126
+ def select_account_for_oidc_resource_owner(owner)
127
+ return_to = return_without_oidc_prompt_param('select_account')
128
+
129
+ instance_exec(
130
+ owner,
131
+ return_to,
132
+ &Doorkeeper::OpenidConnect.configuration.select_account_for_resource_owner
133
+ )
134
+ end
119
135
  end
120
136
  end
121
137
  end
@@ -26,10 +26,8 @@ module Doorkeeper
26
26
  end
27
27
  end
28
28
 
29
- private
30
-
31
29
  def response_on_fragment?
32
- response_type == 'token' || response_type == 'id_token' || response_type == 'id_token token'
30
+ Doorkeeper::OpenidConnect::ResponseMode.new(response_type).fragment?
33
31
  end
34
32
  end
35
33
  end
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Doorkeeper
4
+ module OpenidConnect
5
+ class ResponseMode
6
+ attr_reader :type
7
+
8
+ def initialize(response_type)
9
+ @type = response_type
10
+ end
11
+
12
+ def fragment?
13
+ mode == 'fragment'
14
+ end
15
+
16
+ def query?
17
+ mode == 'query'
18
+ end
19
+
20
+ def mode
21
+ case type
22
+ when 'token', 'id_token', 'id_token token'
23
+ 'fragment'
24
+ else
25
+ 'query'
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
@@ -14,6 +14,4 @@ module Doorkeeper
14
14
  end
15
15
  end
16
16
  end
17
-
18
- Config.prepend OpenidConnect::ResponseTypeConfig
19
17
  end
@@ -2,6 +2,6 @@
2
2
 
3
3
  module Doorkeeper
4
4
  module OpenidConnect
5
- VERSION = '1.7.2'
5
+ VERSION = '1.7.3'
6
6
  end
7
7
  end
@@ -28,6 +28,18 @@ Doorkeeper::OpenidConnect.configure do
28
28
  # redirect_to new_user_session_url
29
29
  end
30
30
 
31
+ # Depending on your configuration, a DoubleRenderError could be raised
32
+ # if render/redirect_to is called at some point before this callback is executed.
33
+ # To avoid the DoubleRenderError, you could add these two lines at the beginning
34
+ # of this callback: (Reference: https://github.com/rails/rails/issues/25106)
35
+ # self.response_body = nil
36
+ # @_response_body = nil
37
+ select_account_for_resource_owner do |resource_owner, return_to|
38
+ # Example implementation:
39
+ # store_location_for resource_owner, return_to
40
+ # redirect_to account_select_url
41
+ end
42
+
31
43
  subject do |resource_owner, application|
32
44
  # Example implementation:
33
45
  # resource_owner.id
@@ -1,7 +1,7 @@
1
1
  class CreateDoorkeeperOpenidConnectTables < ActiveRecord::Migration<%= migration_version %>
2
2
  def change
3
3
  create_table :oauth_openid_requests do |t|
4
- t.integer :access_grant_id, null: false
4
+ t.references :access_grant, null: false, index: true
5
5
  t.string :nonce, null: false
6
6
  end
7
7
 
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: doorkeeper-openid_connect
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.7.2
4
+ version: 1.7.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sam Dengler
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2020-05-20 00:00:00.000000000 Z
12
+ date: 2020-07-06 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: doorkeeper
@@ -157,6 +157,7 @@ files:
157
157
  - lib/doorkeeper/openid_connect/rails/routes.rb
158
158
  - lib/doorkeeper/openid_connect/rails/routes/mapper.rb
159
159
  - lib/doorkeeper/openid_connect/rails/routes/mapping.rb
160
+ - lib/doorkeeper/openid_connect/response_mode.rb
160
161
  - lib/doorkeeper/openid_connect/response_types_config.rb
161
162
  - lib/doorkeeper/openid_connect/user_info.rb
162
163
  - lib/doorkeeper/openid_connect/version.rb
@@ -185,7 +186,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
185
186
  - !ruby/object:Gem::Version
186
187
  version: '0'
187
188
  requirements: []
188
- rubygems_version: 3.0.2
189
+ rubygems_version: 3.0.3
189
190
  signing_key:
190
191
  specification_version: 4
191
192
  summary: OpenID Connect extension for Doorkeeper.