Skip to content
Snippets Groups Projects
Verified Commit a556c020 authored by Ira ¯\_(ツ)_/¯'s avatar Ira ¯\_(ツ)_/¯
Browse files

Add password validation prior to hash generation

parent 82fb8d3f
No related branches found
No related tags found
No related merge requests found
Pipeline #5652 passed
...@@ -13,17 +13,21 @@ import javax.ws.rs.core.Response; ...@@ -13,17 +13,21 @@ import javax.ws.rs.core.Response;
import org.bouncycastle.crypto.generators.OpenBSDBCrypt; import org.bouncycastle.crypto.generators.OpenBSDBCrypt;
import org.jboss.resteasy.annotations.cache.NoCache; import org.jboss.resteasy.annotations.cache.NoCache;
import org.keycloak.models.KeycloakSession; import org.keycloak.models.KeycloakSession;
import org.keycloak.policy.PasswordPolicyManagerProvider;
import org.keycloak.policy.PolicyError;
/** /**
* A custom REST endpoint to trigger functionality on the Keycloak server, which is not available * A custom REST endpoint to trigger functionality on the Keycloak server, which
* through the default set of built-in Keycloak REST endpoints. This is to be used during the * is not available through the default set of built-in Keycloak REST endpoints.
* storage of a custom attribute on the Account Management Console for the mail password. The data * This is to be used during the storage of a custom attribute on the Account
* stored will be a Bcrypt hash instead of the plain text password. * Management Console for the mail password. The data stored will be a Bcrypt
* hash instead of the plain text password.
*/ */
public class MailPassResource { public class MailPassResource {
@SuppressWarnings("unused") @SuppressWarnings("unused")
private final KeycloakSession session; private final KeycloakSession session;
private final String userName;
private static final int SALT_LENGTH = 16; private static final int SALT_LENGTH = 16;
private static final int COST = 12; private static final int COST = 12;
...@@ -37,8 +41,21 @@ public class MailPassResource { ...@@ -37,8 +41,21 @@ public class MailPassResource {
return salt; return salt;
} }
public MailPassResource(KeycloakSession session) { private boolean validatePassword(String pass) {
PasswordPolicyManagerProvider policy = session.getProvider(PasswordPolicyManagerProvider.class);
PolicyError error = policy.validate(this.userName, pass);
if (error != null) {
return false;
}
return true;
}
public MailPassResource(KeycloakSession session, String userName) {
this.session = session; this.session = session;
this.userName = userName;
} }
/** /**
...@@ -64,6 +81,10 @@ public class MailPassResource { ...@@ -64,6 +81,10 @@ public class MailPassResource {
throw new BadRequestException("password object not detected in provided JSON body"); throw new BadRequestException("password object not detected in provided JSON body");
} }
if (!validatePassword(password)) {
throw new BadRequestException("password policy error(length(8) and notUsername)");
}
byte[] salt = generateSalt(); byte[] salt = generateSalt();
String hash = OpenBSDBCrypt.generate(VARIANT, password.toCharArray(), salt, COST); String hash = OpenBSDBCrypt.generate(VARIANT, password.toCharArray(), salt, COST);
......
...@@ -18,6 +18,7 @@ public class MailPassRestResource { ...@@ -18,6 +18,7 @@ public class MailPassRestResource {
private final KeycloakSession session; private final KeycloakSession session;
private final String realmName; private final String realmName;
private final String realmRole; private final String realmRole;
private final String userName;
private final AuthenticationManager.AuthResult auth; private final AuthenticationManager.AuthResult auth;
/** /**
...@@ -30,6 +31,13 @@ public class MailPassRestResource { ...@@ -30,6 +31,13 @@ public class MailPassRestResource {
public MailPassRestResource(KeycloakSession session, String realmName, String realmRole) { public MailPassRestResource(KeycloakSession session, String realmName, String realmRole) {
this.session = session; this.session = session;
this.auth = new AppAuthManager.BearerTokenAuthenticator(session).authenticate(); this.auth = new AppAuthManager.BearerTokenAuthenticator(session).authenticate();
if (auth != null) {
this.userName = this.auth.getUser().getUsername();
} else {
this.userName = "";
}
this.realmName = realmName; this.realmName = realmName;
this.realmRole = realmRole; this.realmRole = realmRole;
} }
...@@ -43,7 +51,7 @@ public class MailPassRestResource { ...@@ -43,7 +51,7 @@ public class MailPassRestResource {
public MailPassResource getMailPassResourceAuthenticated() { public MailPassResource getMailPassResourceAuthenticated() {
checkRealm(); checkRealm();
checkRealmAdmin(); checkRealmAdmin();
return new MailPassResource(session); return new MailPassResource(session, userName);
} }
private void checkRealm() { private void checkRealm() {
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment