From c4892428ae482a8bb14dd834540a02065342d0d7 Mon Sep 17 00:00:00 2001 From: pedroigor Date: Wed, 7 Jan 2015 11:09:40 -0200 Subject: [PATCH] [KEYCLOAK-928] - Validate duplicated emails when updating profile. --- .../resources/LoginActionsService.java | 22 +++++++++++++------ .../RequiredActionUpdateProfileTest.java | 17 ++++++++++++++ .../src/test/resources/testrealm.json | 14 ++++++++++++ 3 files changed, 46 insertions(+), 7 deletions(-) diff --git a/services/src/main/java/org/keycloak/services/resources/LoginActionsService.java b/services/src/main/java/org/keycloak/services/resources/LoginActionsService.java index a9f0233a53..4f462e0a61 100755 --- a/services/src/main/java/org/keycloak/services/resources/LoginActionsService.java +++ b/services/src/main/java/org/keycloak/services/resources/LoginActionsService.java @@ -22,7 +22,6 @@ package org.keycloak.services.resources; import org.jboss.logging.Logger; -import org.jboss.resteasy.specimpl.MultivaluedMapImpl; import org.jboss.resteasy.spi.HttpRequest; import org.keycloak.ClientConnection; import org.keycloak.email.EmailException; @@ -45,7 +44,6 @@ import org.keycloak.models.UserSessionModel; import org.keycloak.models.utils.KeycloakModelUtils; import org.keycloak.models.utils.TimeBasedOTP; import org.keycloak.protocol.LoginProtocol; -import org.keycloak.protocol.oidc.OpenIDConnect; import org.keycloak.protocol.oidc.OpenIDConnectService; import org.keycloak.protocol.oidc.TokenManager; import org.keycloak.representations.PasswordToken; @@ -63,7 +61,6 @@ import javax.ws.rs.POST; import javax.ws.rs.Path; import javax.ws.rs.QueryParam; import javax.ws.rs.core.Context; -import javax.ws.rs.core.Cookie; import javax.ws.rs.core.HttpHeaders; import javax.ws.rs.core.MediaType; import javax.ws.rs.core.MultivaluedMap; @@ -73,7 +70,6 @@ import javax.ws.rs.core.UriInfo; import javax.ws.rs.ext.Providers; import java.util.LinkedList; import java.util.List; -import java.util.UUID; import java.util.concurrent.TimeUnit; /** @@ -605,16 +601,28 @@ public class LoginActionsService { user.setLastName(formData.getFirst("lastName")); String email = formData.getFirst("email"); + String oldEmail = user.getEmail(); boolean emailChanged = oldEmail != null ? !oldEmail.equals(email) : email != null; - user.setEmail(email); + if (emailChanged) { + UserModel userByEmail = session.users().getUserByEmail(email, realm); + + // check for duplicated email + if (userByEmail != null && !userByEmail.getId().equals(user.getId())) { + return Flows.forms(session, realm, null, uriInfo).setUser(user).setError(Messages.EMAIL_EXISTS) + .setClientSessionCode(accessCode.getCode()) + .createResponse(RequiredAction.UPDATE_PROFILE); + } + + user.setEmail(email); + user.setEmailVerified(false); + } user.removeRequiredAction(RequiredAction.UPDATE_PROFILE); - event.clone().event(EventType.UPDATE_PROFILE).success(); + if (emailChanged) { - user.setEmailVerified(false); event.clone().event(EventType.UPDATE_EMAIL).detail(Details.PREVIOUS_EMAIL, oldEmail).detail(Details.UPDATED_EMAIL, email).success(); } diff --git a/testsuite/integration/src/test/java/org/keycloak/testsuite/actions/RequiredActionUpdateProfileTest.java b/testsuite/integration/src/test/java/org/keycloak/testsuite/actions/RequiredActionUpdateProfileTest.java index f66c88e72b..d832f967ee 100755 --- a/testsuite/integration/src/test/java/org/keycloak/testsuite/actions/RequiredActionUpdateProfileTest.java +++ b/testsuite/integration/src/test/java/org/keycloak/testsuite/actions/RequiredActionUpdateProfileTest.java @@ -147,4 +147,21 @@ public class RequiredActionUpdateProfileTest { events.assertEmpty(); } + @Test + public void updateProfileDuplicatedEmail() { + loginPage.open(); + + loginPage.login("test-user@localhost", "password"); + + updateProfilePage.assertCurrent(); + + updateProfilePage.update("New first", "New last", "keycloak-user@localhost"); + + updateProfilePage.assertCurrent(); + + Assert.assertEquals("Email already exists", updateProfilePage.getError()); + + events.assertEmpty(); + } + } diff --git a/testsuite/integration/src/test/resources/testrealm.json b/testsuite/integration/src/test/resources/testrealm.json index cc2a6143d3..81a442d7a8 100755 --- a/testsuite/integration/src/test/resources/testrealm.json +++ b/testsuite/integration/src/test/resources/testrealm.json @@ -29,6 +29,20 @@ "test-app": [ "customer-user" ], "account": [ "view-profile", "manage-account" ] } + }, + { + "username" : "keycloak-user@localhost", + "enabled": true, + "email" : "keycloak-user@localhost", + "credentials" : [ + { "type" : "password", + "value" : "password" } + ], + "realmRoles": ["user"], + "applicationRoles": { + "test-app": [ "customer-user" ], + "account": [ "view-profile", "manage-account" ] + } } ], "oauthClients" : [