use of org.keycloak.models.ModelException in project keycloak by keycloak.
the class LDAPOperationManager method renameEntry.
/**
* Rename LDAPObject name (DN)
*
* @param oldDn
* @param newDn
* @param fallback With fallback=true, we will try to find the another DN in case of conflict. For example if there is an
* attempt to rename to "CN=John Doe", but there is already existing "CN=John Doe", we will try "CN=John Doe0"
* @return the non-conflicting DN, which was used in the end
*/
public String renameEntry(String oldDn, String newDn, boolean fallback) {
try {
String newNonConflictingDn = execute(new LdapOperation<String>() {
@Override
public String execute(LdapContext context) throws NamingException {
String dn = newDn;
// Max 5 attempts for now
int max = 5;
for (int i = 0; i < max; i++) {
try {
context.rename(new LdapName(oldDn), new LdapName(dn));
return dn;
} catch (NameAlreadyBoundException ex) {
if (!fallback) {
throw ex;
} else {
String failedDn = dn;
if (i < max) {
dn = findNextDNForFallback(newDn, i);
logger.warnf("Failed to rename DN [%s] to [%s]. Will try to fallback to DN [%s]", oldDn, failedDn, dn);
} else {
logger.warnf("Failed all fallbacks for renaming [%s]", oldDn);
throw ex;
}
}
}
}
throw new ModelException("Could not rename entry from DN [" + oldDn + "] to new DN [" + newDn + "]. All fallbacks failed");
}
@Override
public String toString() {
return new StringBuilder("LdapOperation: renameEntry\n").append(" oldDn: ").append(oldDn).append("\n").append(" newDn: ").append(newDn).toString();
}
});
return newNonConflictingDn;
} catch (NamingException e) {
throw new ModelException("Could not rename entry from DN [" + oldDn + "] to new DN [" + newDn + "]", e);
}
}
use of org.keycloak.models.ModelException in project keycloak by keycloak.
the class LDAPStorageProvider method proxy.
protected UserModel proxy(RealmModel realm, UserModel local, LDAPObject ldapObject, boolean newUser) {
UserModel existing = userManager.getManagedProxiedUser(local.getId());
if (existing != null) {
return existing;
}
// We need to avoid having CachedUserModel as cache is upper-layer then LDAP. Hence having CachedUserModel here may cause StackOverflowError
if (local instanceof CachedUserModel) {
local = session.userStorageManager().getUserById(realm, local.getId());
existing = userManager.getManagedProxiedUser(local.getId());
if (existing != null) {
return existing;
}
}
UserModel proxied = local;
checkDNChanged(realm, local, ldapObject);
switch(editMode) {
case READ_ONLY:
if (model.isImportEnabled()) {
proxied = new ReadonlyLDAPUserModelDelegate(local);
} else {
proxied = new ReadOnlyUserModelDelegate(local);
}
break;
case WRITABLE:
case UNSYNCED:
// This check is skipped when register new user as there are many "generic" attributes always written (EG. enabled, emailVerified) and those are usually unsupported by LDAP schema
if (!model.isImportEnabled() && !newUser) {
UserModel readOnlyDelegate = new ReadOnlyUserModelDelegate(local, ModelException::new);
proxied = new LDAPWritesOnlyUserModelDelegate(readOnlyDelegate, this);
}
break;
}
AtomicReference<UserModel> proxy = new AtomicReference<>(proxied);
realm.getComponentsStream(model.getId(), LDAPStorageMapper.class.getName()).sorted(ldapMappersComparator.sortAsc()).forEachOrdered(mapperModel -> {
LDAPStorageMapper ldapMapper = mapperManager.getMapper(mapperModel);
proxy.set(ldapMapper.proxy(ldapObject, proxy.get(), realm));
});
proxied = proxy.get();
if (!model.isImportEnabled()) {
proxied = new UpdateOnlyChangeUserModelDelegate(proxied);
}
userManager.setManagedProxiedUser(proxied, ldapObject);
return proxied;
}
use of org.keycloak.models.ModelException in project keycloak by keycloak.
the class MapResourceServerStore method create.
@Override
public ResourceServer create(ClientModel client) {
String clientId = client.getId();
LOG.tracef("create(%s)%s", clientId, getShortStackTrace());
if (clientId == null)
return null;
if (!StorageId.isLocalStorage(clientId)) {
throw new ModelException("Creating resource server from federated ClientModel not supported");
}
if (tx.read(clientId) != null) {
throw new ModelDuplicateException("Resource server already exists: " + clientId);
}
MapResourceServerEntity entity = new MapResourceServerEntityImpl();
entity.setId(clientId);
return entityToAdapter(tx.create(entity));
}
use of org.keycloak.models.ModelException in project keycloak by keycloak.
the class MigrateTo14_0_0 method migrateRealm.
private void migrateRealm(KeycloakSession session, RealmModel realm) {
try {
session.clientPolicy().updateClientProfiles(realm, new ClientProfilesRepresentation());
session.clientPolicy().updateClientPolicies(realm, new ClientPoliciesRepresentation());
} catch (ClientPolicyException cpe) {
throw new ModelException("Exception during migration client profiles or client policies", cpe);
}
}
use of org.keycloak.models.ModelException in project keycloak by keycloak.
the class AccountFormService method processPasswordUpdate.
/**
* Update account password
* <p>
* Form params:
* <p>
* password - old password
* password-new
* pasword-confirm
*
* @return
*/
@Path("password")
@POST
@Consumes(MediaType.APPLICATION_FORM_URLENCODED)
public Response processPasswordUpdate() {
MultivaluedMap<String, String> formData = request.getDecodedFormParameters();
if (auth == null) {
return login("password");
}
auth.require(AccountRoles.MANAGE_ACCOUNT);
csrfCheck(formData);
UserModel user = auth.getUser();
boolean requireCurrent = isPasswordSet(session, realm, user);
account.setPasswordSet(requireCurrent);
String password = formData.getFirst("password");
String passwordNew = formData.getFirst("password-new");
String passwordConfirm = formData.getFirst("password-confirm");
EventBuilder errorEvent = event.clone().event(EventType.UPDATE_PASSWORD_ERROR).client(auth.getClient()).user(auth.getSession().getUser());
if (requireCurrent) {
if (Validation.isBlank(password)) {
setReferrerOnPage();
errorEvent.error(Errors.PASSWORD_MISSING);
return account.setError(Status.OK, Messages.MISSING_PASSWORD).createResponse(AccountPages.PASSWORD);
}
UserCredentialModel cred = UserCredentialModel.password(password);
if (!session.userCredentialManager().isValid(realm, user, cred)) {
setReferrerOnPage();
errorEvent.error(Errors.INVALID_USER_CREDENTIALS);
return account.setError(Status.OK, Messages.INVALID_PASSWORD_EXISTING).createResponse(AccountPages.PASSWORD);
}
}
if (Validation.isBlank(passwordNew)) {
setReferrerOnPage();
errorEvent.error(Errors.PASSWORD_MISSING);
return account.setError(Status.OK, Messages.MISSING_PASSWORD).createResponse(AccountPages.PASSWORD);
}
if (!passwordNew.equals(passwordConfirm)) {
setReferrerOnPage();
errorEvent.error(Errors.PASSWORD_CONFIRM_ERROR);
return account.setError(Status.OK, Messages.INVALID_PASSWORD_CONFIRM).createResponse(AccountPages.PASSWORD);
}
try {
session.userCredentialManager().updateCredential(realm, user, UserCredentialModel.password(passwordNew, false));
} catch (ReadOnlyException mre) {
setReferrerOnPage();
errorEvent.error(Errors.NOT_ALLOWED);
return account.setError(Response.Status.BAD_REQUEST, Messages.READ_ONLY_PASSWORD).createResponse(AccountPages.PASSWORD);
} catch (ModelException me) {
ServicesLogger.LOGGER.failedToUpdatePassword(me);
setReferrerOnPage();
errorEvent.detail(Details.REASON, me.getMessage()).error(Errors.PASSWORD_REJECTED);
return account.setError(Response.Status.NOT_ACCEPTABLE, me.getMessage(), me.getParameters()).createResponse(AccountPages.PASSWORD);
} catch (Exception ape) {
ServicesLogger.LOGGER.failedToUpdatePassword(ape);
setReferrerOnPage();
errorEvent.detail(Details.REASON, ape.getMessage()).error(Errors.PASSWORD_REJECTED);
return account.setError(Response.Status.INTERNAL_SERVER_ERROR, ape.getMessage()).createResponse(AccountPages.PASSWORD);
}
session.sessions().getUserSessionsStream(realm, user).filter(s -> !Objects.equals(s.getId(), auth.getSession().getId())).collect(// collect to avoid concurrent modification as backchannelLogout removes the user sessions.
Collectors.toList()).forEach(s -> AuthenticationManager.backchannelLogout(session, realm, s, session.getContext().getUri(), clientConnection, headers, true));
event.event(EventType.UPDATE_PASSWORD).client(auth.getClient()).user(auth.getUser()).success();
setReferrerOnPage();
return account.setPasswordSet(true).setSuccess(Messages.ACCOUNT_PASSWORD_UPDATED).createResponse(AccountPages.PASSWORD);
}
Aggregations