Class: KeycloakAdmin::UserClient

Inherits:
Client
  • Object
show all
Defined in:
lib/keycloak-admin/client/user_client.rb

Instance Method Summary collapse

Methods inherited from Client

#create_payload, #created_id, #current_token, #execute_http, #headers, #server_url

Constructor Details

#initialize(configuration, realm_client) ⇒ UserClient

Returns a new instance of UserClient.

Raises:

  • (ArgumentError)


4
5
6
7
8
# File 'lib/keycloak-admin/client/user_client.rb', line 4

def initialize(configuration, realm_client)
  super(configuration)
  raise ArgumentError.new("realm must be defined") unless realm_client.name_defined?
  @realm_client = realm_client
end

Instance Method Details

#add_client_roles_on_user(user_id, client_id, role_representations) ⇒ Object



67
68
69
70
71
72
73
# File 'lib/keycloak-admin/client/user_client.rb', line 67

def add_client_roles_on_user(user_id, client_id, role_representations)
  execute_http do
    resource(user_client_role_mappings_url(user_id, client_id)).post(
      create_payload(role_representations), headers
    )
  end
end

#add_group(user_id, group_id) ⇒ Object



40
41
42
43
44
45
46
47
48
49
50
51
52
# File 'lib/keycloak-admin/client/user_client.rb', line 40

def add_group(user_id, group_id)
  execute_http do
    Resource.execute(
      connection_options.merge(
        method: :put,
        url: "#{users_url(user_id)}/groups/#{encode_segment(group_id)}",
        payload: create_payload({}),
        headers: headers,
        logger: @configuration.logger
      )
    )
  end
end

#create!(username, email, password, email_verified, locale, attributes = {}) ⇒ Object

Reads the id of the new user off the Location header rather than searching for it afterwards: Keycloak's search parameter matches a substring of the username, email, first name or last name, so an existing user merely containing this email was returned instead of the one just created.



14
15
16
17
# File 'lib/keycloak-admin/client/user_client.rb', line 14

def create!(username, email, password, email_verified, locale, attributes={})
  response = post_user(build(username, email, password, email_verified, locale, attributes))
  get(created_id(response))
end

#credentials(user_id) ⇒ Object



141
142
143
144
145
146
# File 'lib/keycloak-admin/client/user_client.rb', line 141

def credentials(user_id)
  response = execute_http do
    resource(credentials_url(user_id)).get(headers)
  end
  JSON.parse(response).map { |group_as_hash| CredentialRepresentation.from_hash(group_as_hash) }
end

#credentials_url(user_id) ⇒ Object

Raises:

  • (ArgumentError)


264
265
266
267
# File 'lib/keycloak-admin/client/user_client.rb', line 264

def credentials_url(user_id)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?
  "#{users_url(user_id)}/credentials"
end

#delete(user_id) ⇒ Object



112
113
114
115
116
117
# File 'lib/keycloak-admin/client/user_client.rb', line 112

def delete(user_id)
  execute_http do
    resource(users_url(user_id)).delete(headers)
  end
  true
end

#execute_actions_email(user_id, actions = [], lifespan = nil, redirect_uri = nil, client_id = nil) ⇒ Object

Raises:

  • (ArgumentError)


152
153
154
155
156
157
158
159
160
161
162
163
164
165
# File 'lib/keycloak-admin/client/user_client.rb', line 152

def execute_actions_email(user_id, actions=[], lifespan=nil, redirect_uri=nil, client_id=nil)
  raise ArgumentError.new("client_id must be defined") if client_id.nil? && !redirect_uri.nil?
  execute_http do
    query = {}
    query[:client_id]    = client_id     unless client_id.nil?
    query[:redirect_uri] = redirect_uri  unless redirect_uri.nil?
    query[:lifespan]     = lifespan.to_i unless lifespan.nil?

    url = execute_actions_email_url(user_id)
    url = "#{url}?#{build_query(query)}" unless query.empty?
    resource(url).put(create_payload(actions), headers)
  end
  user_id
end

#execute_actions_email_url(user_id) ⇒ Object

Raises:

  • (ArgumentError)


254
255
256
257
# File 'lib/keycloak-admin/client/user_client.rb', line 254

def execute_actions_email_url(user_id)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?
  "#{users_url(user_id)}/execute-actions-email"
end

#federated_identity_url(user_id, identity_provider) ⇒ Object

Raises:

  • (ArgumentError)


274
275
276
277
278
# File 'lib/keycloak-admin/client/user_client.rb', line 274

def federated_identity_url(user_id, identity_provider)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?
  raise ArgumentError.new("identity_provider must be defined") if identity_provider.nil?
  "#{users_url(user_id)}/federated-identity/#{encode_segment(identity_provider)}"
end

#forgot_password(user_id, lifespan = nil) ⇒ Object



148
149
150
# File 'lib/keycloak-admin/client/user_client.rb', line 148

def forgot_password(user_id, lifespan=nil)
  execute_actions_email(user_id, ["UPDATE_PASSWORD"], lifespan)
end

#get(user_id) ⇒ Object



75
76
77
78
79
80
# File 'lib/keycloak-admin/client/user_client.rb', line 75

def get(user_id)
  response = execute_http do
    resource(users_url(user_id)).get(headers)
  end
  UserRepresentation.from_hash(JSON.parse(response))
end

#get_redirect_impersonation(user_id) ⇒ Object



208
209
210
# File 'lib/keycloak-admin/client/user_client.rb', line 208

def get_redirect_impersonation(user_id)
  ImpersonationRedirectionRepresentation.from_url(impersonation_url(user_id), headers)
end

#groups(user_id) ⇒ Object



119
120
121
122
123
124
# File 'lib/keycloak-admin/client/user_client.rb', line 119

def groups(user_id)
  response = execute_http do
    resource(groups_url(user_id)).get(headers)
  end
  JSON.parse(response).map { |group_as_hash| GroupRepresentation.from_hash(group_as_hash) }
end

#groups_url(user_id) ⇒ Object

Raises:

  • (ArgumentError)


259
260
261
262
# File 'lib/keycloak-admin/client/user_client.rb', line 259

def groups_url(user_id)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?
  "#{users_url(user_id)}/groups"
end

#impersonate(user_id) ⇒ Object



167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
# File 'lib/keycloak-admin/client/user_client.rb', line 167

def impersonate(user_id)
  response = execute_http do
    impersonation = get_redirect_impersonation(user_id)
    Resource.execute(
      connection_options.merge(
        method: :post,
        url: impersonation.impersonation_url,
        payload: impersonation.body.to_json,
        headers: impersonation.headers,
        logger: @configuration.logger
      )
    )
  end
  ImpersonationRepresentation.from_response(response, @configuration.server_domain)
end

#impersonation_url(user_id) ⇒ Object

Raises:

  • (ArgumentError)


269
270
271
272
# File 'lib/keycloak-admin/client/user_client.rb', line 269

def impersonation_url(user_id)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?
  "#{users_url(user_id)}/impersonation"
end


212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
# File 'lib/keycloak-admin/client/user_client.rb', line 212

def link_idp(user_id, idp_id, idp_user_id, idp_username)
  fed_id_rep                   = FederatedIdentityRepresentation.new
  fed_id_rep.user_id           = idp_user_id
  fed_id_rep.user_name         = idp_username
  fed_id_rep.identity_provider = idp_id

  execute_http do
    Resource.execute(
      connection_options.merge(
        method: :post,
        url: federated_identity_url(user_id, idp_id),
        payload: fed_id_rep.to_json,
        headers: headers,
        logger: @configuration.logger
      )
    )
  end
end

#list(first: nil, max: nil) ⇒ Object

Keycloak answers this endpoint with at most 100 users unless max says otherwise, so a bare list silently truncates a larger realm. Passing neither bound sends no query parameter at all, exactly as before.



107
108
109
110
# File 'lib/keycloak-admin/client/user_client.rb', line 107

def list(first: nil, max: nil)
  pagination = {first: first, max: max}.compact
  search(pagination.empty? ? nil : pagination)
end

#logout(user_id) ⇒ Object

Raises:

  • (ArgumentError)


192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
# File 'lib/keycloak-admin/client/user_client.rb', line 192

def logout(user_id)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?

  execute_http do
    Resource.execute(
      connection_options.merge(
        method: :post,
        url: logout_url(user_id),
        headers: headers,
        logger: @configuration.logger
      )
    )
  end
  true
end

#logout_url(user_id) ⇒ Object

Raises:

  • (ArgumentError)


280
281
282
283
284
# File 'lib/keycloak-admin/client/user_client.rb', line 280

def logout_url(user_id)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?

  "#{users_url(user_id)}/logout"
end

#remove_group(user_id, group_id) ⇒ Object



54
55
56
57
58
59
60
61
62
63
64
65
# File 'lib/keycloak-admin/client/user_client.rb', line 54

def remove_group(user_id, group_id)
  execute_http do
    Resource.execute(
      connection_options.merge(
        method: :delete,
        url: "#{users_url(user_id)}/groups/#{encode_segment(group_id)}",
        headers: headers,
        logger: @configuration.logger
      )
    )
  end
end

#reset_password_url(user_id) ⇒ Object

Raises:

  • (ArgumentError)


249
250
251
252
# File 'lib/keycloak-admin/client/user_client.rb', line 249

def reset_password_url(user_id)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?
  "#{users_url(user_id)}/reset-password"
end

#save(user_representation) ⇒ Object



19
20
21
22
# File 'lib/keycloak-admin/client/user_client.rb', line 19

def save(user_representation)
  post_user(user_representation)
  user_representation
end

#search(query) ⇒ Object

Query can be a string or a hash.



88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
# File 'lib/keycloak-admin/client/user_client.rb', line 88

def search(query)
  derived_headers = case query
                    when String
                      headers.merge({params: { search: query }})
                    when Hash
                      headers.merge({params: query })
                    else
                      headers
                    end

  response = execute_http do
    resource(users_url).get(derived_headers)
  end
  JSON.parse(response).map { |user_as_hash| UserRepresentation.from_hash(user_as_hash) }
end

#sessions(user_id) ⇒ Object

Raises:

  • (ArgumentError)


183
184
185
186
187
188
189
190
# File 'lib/keycloak-admin/client/user_client.rb', line 183

def sessions(user_id)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?

  response = execute_http do
    resource("#{users_url(user_id)}/sessions").get(headers)
  end
  JSON.parse(response).map { |session_as_hash| SessionRepresentation.from_hash(session_as_hash) }
end


231
232
233
234
235
# File 'lib/keycloak-admin/client/user_client.rb', line 231

def unlink_idp(user_id, idp_id)
  execute_http do
    resource(federated_identity_url(user_id, idp_id)).delete(headers)
  end
end

#update(user_id, user_representation_body) ⇒ Object

pay attention that, since Keycloak 24.0.4, partial updates of attributes are not authorized anymore

Raises:

  • (ArgumentError)


25
26
27
28
29
30
31
32
33
34
35
36
37
38
# File 'lib/keycloak-admin/client/user_client.rb', line 25

def update(user_id, user_representation_body)
  raise ArgumentError.new("user_id must be defined") if user_id.nil?
  execute_http do
    Resource.execute(
      connection_options.merge(
        method: :put,
        url: users_url(user_id),
        payload: create_payload(user_representation_body),
        headers: headers,
        logger: @configuration.logger
      )
    )
  end
end

#update_password(user_id, new_password, temporary: false) ⇒ Object



126
127
128
129
130
131
132
133
134
135
136
137
138
139
# File 'lib/keycloak-admin/client/user_client.rb', line 126

def update_password(user_id, new_password, temporary: false)
  execute_http do
    Resource.execute(
      connection_options.merge(
        method: :put,
        url: reset_password_url(user_id),
        payload: { type: "password", value: new_password, temporary: temporary }.to_json,
        headers: headers,
        logger: @configuration.logger
      )
    )
  end
  user_id
end

#user_client_role_mappings_url(user_id, client_id) ⇒ Object



245
246
247
# File 'lib/keycloak-admin/client/user_client.rb', line 245

def user_client_role_mappings_url(user_id, client_id)
  "#{users_url(user_id)}/role-mappings/clients/#{encode_segment(client_id)}"
end

#users_url(id = nil) ⇒ Object



237
238
239
240
241
242
243
# File 'lib/keycloak-admin/client/user_client.rb', line 237

def users_url(id=nil)
  if id
    "#{@realm_client.realm_admin_url}/users/#{encode_segment(id)}"
  else
    "#{@realm_client.realm_admin_url}/users"
  end
end