hydra-keycloak-client 0.1.16 → 0.1.18

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: e21882cde2f44b50a21259216097d6f101429189476d7c8e672a45376445639e
4
- data.tar.gz: 109d00d611d0755b8a8ef9d1ddc564d0b05203bbf52fe09b2bf50d41c58cf62d
3
+ metadata.gz: 0a2e948b3a20ed2ba3bbbfa11c0d8095d1d2668ab7b84ab9c84ee141b4ffd858
4
+ data.tar.gz: 470d447468b40bb7f22ba97126702a7c99952cf9038005097b44651ce900a0c3
5
5
  SHA512:
6
- metadata.gz: 66ece7983e4ed5731233f41ad9d15e4bf6fcb1c55f8e2aa708b3317031ff89f201e9cdf3ec7bc94fc7e5855f9b95b78ed7c53ddfcac085108053893719072b27
7
- data.tar.gz: a1edbad85e6397ae3ea3f1f6e66c3f0cecc16648e4b344d900ac16c71a2904ac450041615cc022319421380b39837a93abd4e5765ec3c6dcc1e196e70483785e
6
+ metadata.gz: ce821ea5c0d68d23c1e57c5696013b4a3cdec84e4bd70e1ad484c2c394e1fa5699f7b685311732c4ed8d176406faeece9b78e722cb53fae7666c69e77cb9dfa5
7
+ data.tar.gz: fdb9094dd2861753b689f2a83b367116460b49f0a3817d2ba01b1c2fcf5ea705d2e4c7f903b6131c6d137c2785a8e5572ed9c80f74959447a37e9238a2eadecb
data/.gitignore CHANGED
@@ -1,3 +1,6 @@
1
1
  .rspec_status
2
2
  coverage
3
3
  .bundle
4
+ .DS_Store
5
+ .idea
6
+ .ruby-version
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- hydra-keycloak-client (0.1.16)
4
+ hydra-keycloak-client (0.1.18)
5
5
  dry-auto_inject
6
6
  dry-container
7
7
  dry-monads
@@ -127,7 +127,12 @@ module Hydra
127
127
  class Client
128
128
  extend ::Hydra::Keycloak::Mixin
129
129
  include ::Dry::Monads[:result, :do]
130
- inject['urls', 'tokens_repo', 'store', 'code_verifier']
130
+ inject[
131
+ 'urls',
132
+ 'tokens_repo',
133
+ 'store',
134
+ 'code_verifier'
135
+ ]
131
136
 
132
137
  def auth_url
133
138
  code_verifier.generate
@@ -171,17 +176,17 @@ module Hydra
171
176
  end
172
177
 
173
178
  def access_token(session_state)
174
- return Failure(status: 400, code: :not_authenticated) unless authenticated?(session_state)
175
-
176
179
  fetch_token(session_state, 'access_token')
180
+ .or(Failure(code: :not_authenticated,
181
+ context: { args: { session_state: session_state } }))
177
182
  end
178
183
 
179
184
  def authorize!(session_state)
180
- return Failure(status: 400, code: :not_authenticated) unless authenticated?(session_state)
181
-
182
185
  access_token = yield fetch_token(session_state, 'access_token')
186
+ .or(Failure(code: :not_authenticated,
187
+ context: { args: { session_state: session_state } }))
183
188
  if token_expired?(access_token)
184
- refresh_tokens(session_state)
189
+ yield refresh_tokens(session_state)
185
190
 
186
191
  access_token = yield fetch_token(session_state, 'access_token')
187
192
  end
@@ -190,17 +195,17 @@ module Hydra
190
195
  end
191
196
 
192
197
  def access_token_jti(session_state)
193
- return Failure(status: 400, code: :not_authenticated) unless authenticated?(session_state)
194
-
195
- fetch_token(session_state, 'access_token').fmap(&:jti)
198
+ fetch_token(session_state, 'access_token')
199
+ .either(->(token) { Success(token[:jti]) },
200
+ ->(_) { Failure(code: :not_authenticated, context: { args: { session_state: session_state } }) })
196
201
  end
197
202
 
198
203
  def logout!(session_state)
199
- fetch_token(session_state, 'id_token').bind do |id_token|
200
- clear_tokens(session_state)
204
+ id_token = yield fetch_token(session_state, 'id_token')
201
205
 
202
- urls.end_session_url(id_token.source)
203
- end
206
+ yield clear_tokens(session_state)
207
+
208
+ Success(urls.end_session_url(id_token.source))
204
209
  end
205
210
 
206
211
  def introspect_token(token)
@@ -218,15 +223,22 @@ module Hydra
218
223
  if value
219
224
  Success(::Hydra::Keycloak::Token.new(value))
220
225
  else
221
- Failure(status: 400, code: :token_not_found)
226
+ Failure(code: :token_not_found,
227
+ context: { args: { session_state: session_state,
228
+ token_name: token_name } })
222
229
  end
223
230
  end
224
231
  end
225
232
 
226
233
  def clear_tokens(session_state)
227
- store.delete("#{session_state}_access_token")
228
- store.delete("#{session_state}_id_token")
229
- store.delete("#{session_state}_refresh_token")
234
+ Dry::Monads::List[
235
+ "#{session_state}_access_token",
236
+ "#{session_state}_id_token",
237
+ "#{session_state}_refresh_token"
238
+ ]
239
+ .fmap { |x| store.delete(x) }
240
+ .typed(Dry::Monads::Result)
241
+ .traverse
230
242
  end
231
243
 
232
244
  def token_expired?(token)
@@ -240,6 +252,8 @@ module Hydra
240
252
  yield save_token(session_state, 'access_token', new_tokens[:access_token])
241
253
  yield save_token(session_state, 'id_token', new_tokens[:id_token])
242
254
  yield save_token(session_state, 'refresh_token', new_tokens[:refresh_token])
255
+
256
+ Success()
243
257
  end
244
258
  end
245
259
  end
@@ -15,22 +15,22 @@ module Hydra
15
15
  dalli.set(key, value)
16
16
 
17
17
  Success(:ok)
18
- rescue Dalli::DalliError
19
- Failure(status: 400, code: :memcached_unavailable)
18
+ rescue Dalli::DalliError => e
19
+ Failure(code: :memcached_unavailable, context: { args: { key: key }, action: :set, error: e.message })
20
20
  end
21
21
 
22
22
  def get(key)
23
23
  Success(dalli.get(key))
24
- rescue Dalli::DalliError
25
- Failure(status: 400, code: :memcached_unavailable)
24
+ rescue Dalli::DalliError => e
25
+ Failure(code: :memcached_unavailable, context: { args: { key: key }, action: :get, error: e.message })
26
26
  end
27
27
 
28
28
  def delete(key)
29
29
  dalli.delete(key)
30
30
 
31
31
  Success(:ok)
32
- rescue Dalli::DalliError
33
- Failure(status: 400, code: :memcached_unavailable)
32
+ rescue Dalli::DalliError => e
33
+ Failure(code: :memcached_unavailable, context: { args: { key: key }, action: :delete, error: e.message })
34
34
  end
35
35
  end
36
36
  end
@@ -15,22 +15,22 @@ module Hydra
15
15
  redis.set(key, value)
16
16
 
17
17
  Success(:ok)
18
- rescue Redis::BaseError
19
- Failure(status: 400, code: :redis_unavailable)
18
+ rescue Redis::BaseError => e
19
+ Failure(code: :redis_unavailable, context: { args: { key: key }, action: :set, error: e.message })
20
20
  end
21
21
 
22
22
  def get(key)
23
23
  Success(redis.get(key))
24
- rescue Redis::BaseError
25
- Failure(status: 400, code: :redis_unavailable)
24
+ rescue Redis::BaseError => e
25
+ Failure(code: :redis_unavailable, context: { args: { key: key }, action: :get, error: e.message })
26
26
  end
27
27
 
28
28
  def delete(key)
29
29
  redis.del(key)
30
30
 
31
31
  Success(:ok)
32
- rescue Redis::BaseError
33
- Failure(status: 400, code: :redis_unavailable)
32
+ rescue Redis::BaseError => e
33
+ Failure(code: :redis_unavailable, context: { args: { key: key }, action: :delete, error: e.message })
34
34
  end
35
35
  end
36
36
  end
@@ -25,19 +25,45 @@ module Hydra
25
25
  Net::ProtocolError].freeze
26
26
 
27
27
  def post(path, body)
28
- response = http.post_form(URI(path), body)
28
+ _post(URI(path), body)
29
+ .bind { |resp| parse_response(resp.body) }
30
+ end
29
31
 
30
- if response.code == '200'
31
- json = JSON.parse(response.body)
32
+ private
32
33
 
33
- Success(json)
34
+ def _post(path, body)
35
+ response = http.post_form(URI(path), body)
36
+
37
+ if %w[200 201].include?(response.code)
38
+ Success(response)
34
39
  else
35
- Failure(status: response.code, code: :bad_keycloak_response)
40
+ Failure(code: :bad_keycloak_response,
41
+ context: { args: { path: path,
42
+ body: hide_secrets(body) },
43
+ method: :post,
44
+ response: { code: response.code,
45
+ body: response.body } })
36
46
  end
37
- rescue *NETWORK_ERRORS
38
- Failure(status: 400, code: :keycloak_unavailable)
39
- rescue JSON::ParserError
40
- Failure(status: 400, code: :json_parser_error)
47
+ rescue *NETWORK_ERRORS => e
48
+ Failure(code: :keycloak_unavailable, context: { error: e.message })
49
+ end
50
+
51
+ def parse_response(body)
52
+ Success(JSON.parse(body))
53
+ rescue JSON::ParserError => e
54
+ Failure(code: :json_parser_error, context: { args: { body: body }, error: e.message })
55
+ end
56
+
57
+ def hide_secrets(body)
58
+ secret_fields = %i[client_secret]
59
+
60
+ body.map do |k, v|
61
+ if secret_fields.include?(k)
62
+ [k, '**hidden**']
63
+ else
64
+ [k, v]
65
+ end
66
+ end.to_h
41
67
  end
42
68
  end
43
69
  end
@@ -14,7 +14,7 @@ module Hydra
14
14
  inject['tokens_gateway', 'urls']
15
15
 
16
16
  def get_tokens(auth_code, code_verifier)
17
- return Failure(status: 400, code: :auth_code_was_not_received) unless auth_code
17
+ return Failure(code: :auth_code_was_not_received) unless auth_code
18
18
 
19
19
  result = tokens_gateway.post(
20
20
  urls.token_endpoint,
@@ -31,7 +31,7 @@ module Hydra
31
31
  end
32
32
 
33
33
  def get_tokens_by_password(username, password)
34
- return Failure(status: 400, code: :username_or_password_is_empty) if username.nil? || password.nil?
34
+ return Failure(code: :username_or_password_is_empty) if username.nil? || password.nil?
35
35
 
36
36
  result = tokens_gateway.post(
37
37
  urls.token_endpoint,
@@ -55,7 +55,7 @@ module Hydra
55
55
  if result['active']
56
56
  Success(result)
57
57
  else
58
- Failure(status: 400, code: :token_not_active)
58
+ Failure(code: :token_not_active)
59
59
  end
60
60
  end
61
61
  end
@@ -65,15 +65,9 @@ module Hydra
65
65
  urls.token_endpoint,
66
66
  urls.refresh_request_body(refresh_token)
67
67
  ).bind do |result|
68
- if result['error']
69
- Failure(status: 400, code: :token_refreshing_error)
70
- else
71
- Success({
72
- access_token: ::Hydra::Keycloak::Token.new(result['access_token']),
73
- id_token: ::Hydra::Keycloak::Token.new(result['id_token']),
74
- refresh_token: ::Hydra::Keycloak::Token.new(result['refresh_token'])
75
- })
76
- end
68
+ Success({ access_token: ::Hydra::Keycloak::Token.new(result['access_token']),
69
+ id_token: ::Hydra::Keycloak::Token.new(result['id_token']),
70
+ refresh_token: ::Hydra::Keycloak::Token.new(result['refresh_token']) })
77
71
  end
78
72
  end
79
73
  end
@@ -2,6 +2,6 @@
2
2
 
3
3
  module Hydra
4
4
  module Keycloak
5
- VERSION = '0.1.16'
5
+ VERSION = '0.1.18'
6
6
  end
7
7
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: hydra-keycloak-client
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.16
4
+ version: 0.1.18
5
5
  platform: ruby
6
6
  authors:
7
7
  - Fedor Kosolapov
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-02-07 00:00:00.000000000 Z
11
+ date: 2023-02-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: jwt