@@ -19,10 +19,17 @@ | |||
*/ | |||
package org.sonar.server.authentication; | |||
import java.security.NoSuchAlgorithmException; | |||
import java.security.SecureRandom; | |||
import java.security.spec.InvalidKeySpecException; | |||
import java.util.Base64; | |||
import java.util.EnumMap; | |||
import javax.annotation.Nullable; | |||
import javax.crypto.SecretKeyFactory; | |||
import javax.crypto.spec.PBEKeySpec; | |||
import org.apache.commons.codec.digest.DigestUtils; | |||
import org.mindrot.jbcrypt.BCrypt; | |||
import org.sonar.api.config.Configuration; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.user.UserDto; | |||
@@ -39,14 +46,23 @@ import static java.util.Objects.requireNonNull; | |||
* database). | |||
*/ | |||
public class CredentialsLocalAuthentication { | |||
private static final SecureRandom SECURE_RANDOM = new SecureRandom(); | |||
private static final HashMethod DEFAULT = HashMethod.PBKDF2; | |||
private static final String PBKDF2_ITERATIONS_PROP = "sonar.internal.pbkdf2.iterations"; | |||
private final DbClient dbClient; | |||
private static final SecureRandom SECURE_RANDOM = new SecureRandom(); | |||
// The default hash method that must be used is BCRYPT | |||
private static final HashMethod DEFAULT = HashMethod.BCRYPT; | |||
private final EnumMap<HashMethod, HashFunction> hashFunctions = new EnumMap<>(HashMethod.class); | |||
public enum HashMethod { | |||
SHA1, BCRYPT, PBKDF2; | |||
} | |||
public CredentialsLocalAuthentication(DbClient dbClient) { | |||
public CredentialsLocalAuthentication(DbClient dbClient, Configuration configuration) { | |||
this.dbClient = dbClient; | |||
hashFunctions.put(HashMethod.BCRYPT, new BcryptFunction()); | |||
hashFunctions.put(HashMethod.SHA1, new Sha1Function()); | |||
hashFunctions.put(HashMethod.PBKDF2, new PBKDF2Function(configuration.getInt(PBKDF2_ITERATIONS_PROP).orElse(null))); | |||
} | |||
/** | |||
@@ -75,7 +91,9 @@ public class CredentialsLocalAuthentication { | |||
.build(); | |||
} | |||
AuthenticationResult result = hashMethod.checkCredentials(user, password); | |||
HashFunction hashFunction = hashFunctions.get(hashMethod); | |||
AuthenticationResult result = hashFunction.checkCredentials(user, password); | |||
if (!result.isSuccessful()) { | |||
throw AuthenticationException.newBuilder() | |||
.setSource(Source.local(method)) | |||
@@ -85,8 +103,8 @@ public class CredentialsLocalAuthentication { | |||
} | |||
// Upgrade the password if it's an old hashMethod | |||
if (hashMethod != DEFAULT) { | |||
DEFAULT.storeHashPassword(user, password); | |||
if (hashMethod != DEFAULT || result.needsUpdate) { | |||
hashFunctions.get(DEFAULT).storeHashPassword(user, password); | |||
dbClient.userDao().update(session, user); | |||
} | |||
} | |||
@@ -96,37 +114,23 @@ public class CredentialsLocalAuthentication { | |||
* The crypted_password, salt and hash_method are set | |||
*/ | |||
public void storeHashPassword(UserDto user, String password) { | |||
DEFAULT.storeHashPassword(user, password); | |||
} | |||
public enum HashMethod implements HashFunction { | |||
SHA1(new Sha1Function()), BCRYPT(new BcryptFunction()); | |||
private HashFunction hashFunction; | |||
HashMethod(HashFunction hashFunction) { | |||
this.hashFunction = hashFunction; | |||
} | |||
@Override | |||
public AuthenticationResult checkCredentials(UserDto user, String password) { | |||
return hashFunction.checkCredentials(user, password); | |||
} | |||
@Override | |||
public void storeHashPassword(UserDto user, String password) { | |||
hashFunction.storeHashPassword(user, password); | |||
} | |||
hashFunctions.get(DEFAULT).storeHashPassword(user, password); | |||
} | |||
private static class AuthenticationResult { | |||
private final boolean successful; | |||
private final String failureMessage; | |||
private final boolean needsUpdate; | |||
private AuthenticationResult(boolean successful, String failureMessage) { | |||
this(successful, failureMessage, false); | |||
} | |||
private AuthenticationResult(boolean successful, String failureMessage, boolean needsUpdate) { | |||
checkArgument((successful && failureMessage.isEmpty()) || (!successful && !failureMessage.isEmpty()), "Incorrect parameters"); | |||
this.successful = successful; | |||
this.failureMessage = failureMessage; | |||
this.needsUpdate = needsUpdate; | |||
} | |||
public boolean isSuccessful() { | |||
@@ -136,6 +140,10 @@ public class CredentialsLocalAuthentication { | |||
public String getFailureMessage() { | |||
return failureMessage; | |||
} | |||
public boolean isNeedsUpdate() { | |||
return needsUpdate; | |||
} | |||
} | |||
public interface HashFunction { | |||
@@ -179,8 +187,70 @@ public class CredentialsLocalAuthentication { | |||
} | |||
} | |||
private static final class PBKDF2Function implements HashFunction { | |||
private static final int DEFAULT_ITERATIONS = 100_000; | |||
private static final String ALGORITHM = "PBKDF2WithHmacSHA512"; | |||
private static final int KEY_LEN = 512; | |||
private final int gen_iterations; | |||
public PBKDF2Function(@Nullable Integer gen_iterations) { | |||
this.gen_iterations = gen_iterations != null ? gen_iterations : DEFAULT_ITERATIONS; | |||
} | |||
@Override | |||
public AuthenticationResult checkCredentials(UserDto user, String password) { | |||
if (user.getCryptedPassword() == null) { | |||
return new AuthenticationResult(false, "null password in DB"); | |||
} | |||
if (user.getSalt() == null) { | |||
return new AuthenticationResult(false, "null salt"); | |||
} | |||
int pos = user.getCryptedPassword().indexOf('$'); | |||
if (pos < 1) { | |||
return new AuthenticationResult(false, "invalid hash stored"); | |||
} | |||
int iterations; | |||
try { | |||
iterations = Integer.parseInt(user.getCryptedPassword().substring(0, pos)); | |||
} catch (NumberFormatException e) { | |||
return new AuthenticationResult(false, "invalid hash stored"); | |||
} | |||
String hash = user.getCryptedPassword().substring(pos + 1); | |||
byte[] salt = Base64.getDecoder().decode(user.getSalt()); | |||
if (!hash.equals(hash(salt, password, iterations))) { | |||
return new AuthenticationResult(false, "wrong password"); | |||
} | |||
boolean needsUpdate = iterations != gen_iterations; | |||
return new AuthenticationResult(true, "", needsUpdate); | |||
} | |||
@Override | |||
public void storeHashPassword(UserDto user, String password) { | |||
byte[] salt = new byte[20]; | |||
SECURE_RANDOM.nextBytes(salt); | |||
String hashStr = hash(salt, password, gen_iterations); | |||
String saltStr = Base64.getEncoder().encodeToString(salt); | |||
user.setHashMethod(HashMethod.PBKDF2.name()) | |||
.setCryptedPassword(gen_iterations + "$" + hashStr) | |||
.setSalt(saltStr); | |||
} | |||
private String hash(byte[] salt, String password, int iterations) { | |||
try { | |||
SecretKeyFactory skf = SecretKeyFactory.getInstance(ALGORITHM); | |||
PBEKeySpec spec = new PBEKeySpec(password.toCharArray(), salt, iterations, KEY_LEN); | |||
byte[] hash = skf.generateSecret(spec).getEncoded(); | |||
return Base64.getEncoder().encodeToString(hash); | |||
} catch (NoSuchAlgorithmException | InvalidKeySpecException e) { | |||
throw new RuntimeException(e); | |||
} | |||
} | |||
} | |||
/** | |||
* Implementation of bcrypt hash function | |||
* Implementation of deprecated bcrypt hash function | |||
*/ | |||
private static final class BcryptFunction implements HashFunction { | |||
@Override |
@@ -24,6 +24,7 @@ import javax.servlet.http.HttpServletRequest; | |||
import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.junit.rules.ExpectedException; | |||
import org.sonar.api.config.internal.MapSettings; | |||
import org.sonar.api.utils.System2; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
@@ -38,9 +39,9 @@ import static org.mockito.Mockito.verify; | |||
import static org.mockito.Mockito.verifyZeroInteractions; | |||
import static org.mockito.Mockito.when; | |||
import static org.sonar.db.user.UserTesting.newUserDto; | |||
import static org.sonar.server.authentication.event.AuthenticationEvent.Source; | |||
import static org.sonar.server.authentication.event.AuthenticationEvent.Method.BASIC; | |||
import static org.sonar.server.authentication.event.AuthenticationEvent.Method.BASIC_TOKEN; | |||
import static org.sonar.server.authentication.event.AuthenticationEvent.Source; | |||
import static org.sonar.server.authentication.event.AuthenticationExceptionMatcher.authenticationException; | |||
public class CredentialsAuthenticationTest { | |||
@@ -58,8 +59,9 @@ public class CredentialsAuthenticationTest { | |||
private DbSession dbSession = dbTester.getSession(); | |||
private HttpServletRequest request = mock(HttpServletRequest.class); | |||
private AuthenticationEvent authenticationEvent = mock(AuthenticationEvent.class); | |||
private MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private CredentialsExternalAuthentication externalAuthentication = mock(CredentialsExternalAuthentication.class); | |||
private CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(dbClient); | |||
private CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(dbClient, settings.asConfig()); | |||
private CredentialsAuthentication underTest = new CredentialsAuthentication(dbClient, authenticationEvent, externalAuthentication, localAuthentication); | |||
@Test |
@@ -22,10 +22,12 @@ package org.sonar.server.authentication; | |||
import java.util.Optional; | |||
import java.util.Random; | |||
import org.apache.commons.codec.digest.DigestUtils; | |||
import org.junit.Before; | |||
import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.junit.rules.ExpectedException; | |||
import org.mindrot.jbcrypt.BCrypt; | |||
import org.sonar.api.config.internal.MapSettings; | |||
import org.sonar.db.DbTester; | |||
import org.sonar.db.user.UserDto; | |||
import org.sonar.server.authentication.event.AuthenticationEvent; | |||
@@ -35,6 +37,7 @@ import static org.apache.commons.lang.RandomStringUtils.randomAlphanumeric; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.sonar.db.user.UserTesting.newUserDto; | |||
import static org.sonar.server.authentication.CredentialsLocalAuthentication.HashMethod.BCRYPT; | |||
import static org.sonar.server.authentication.CredentialsLocalAuthentication.HashMethod.PBKDF2; | |||
import static org.sonar.server.authentication.CredentialsLocalAuthentication.HashMethod.SHA1; | |||
public class CredentialsLocalAuthenticationTest { | |||
@@ -44,8 +47,14 @@ public class CredentialsLocalAuthenticationTest { | |||
public DbTester db = DbTester.create(); | |||
private static final Random RANDOM = new Random(); | |||
private static final MapSettings settings = new MapSettings(); | |||
private CredentialsLocalAuthentication underTest = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private CredentialsLocalAuthentication underTest = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
@Before | |||
public void setup() { | |||
settings.setProperty("sonar.internal.pbkdf2.iterations", 1); | |||
} | |||
@Test | |||
public void incorrect_hash_should_throw_AuthenticationException() { | |||
@@ -179,10 +188,150 @@ public class CredentialsLocalAuthenticationTest { | |||
Optional<UserDto> myself = db.users().selectUserByLogin("myself"); | |||
assertThat(myself).isPresent(); | |||
assertThat(myself.get().getHashMethod()).isEqualTo(BCRYPT.name()); | |||
assertThat(myself.get().getSalt()).isNull(); | |||
assertThat(myself.get().getHashMethod()).isEqualTo(PBKDF2.name()); | |||
assertThat(myself.get().getSalt()).isNotNull(); | |||
// authentication must work with upgraded hash method | |||
underTest.authenticate(db.getSession(), user, password, AuthenticationEvent.Method.BASIC); | |||
} | |||
@Test | |||
public void authentication_upgrade_hash_function_when_BCRYPT_was_used() { | |||
String password = randomAlphanumeric(60); | |||
byte[] saltRandom = new byte[20]; | |||
RANDOM.nextBytes(saltRandom); | |||
String salt = DigestUtils.sha1Hex(saltRandom); | |||
UserDto user = newUserDto() | |||
.setLogin("myself") | |||
.setHashMethod(BCRYPT.name()) | |||
.setCryptedPassword(BCrypt.hashpw(password, BCrypt.gensalt(12))) | |||
.setSalt(salt); | |||
db.users().insertUser(user); | |||
underTest.authenticate(db.getSession(), user, password, AuthenticationEvent.Method.BASIC); | |||
Optional<UserDto> myself = db.users().selectUserByLogin("myself"); | |||
assertThat(myself).isPresent(); | |||
assertThat(myself.get().getHashMethod()).isEqualTo(PBKDF2.name()); | |||
assertThat(myself.get().getSalt()).isNotNull(); | |||
// authentication must work with upgraded hash method | |||
underTest.authenticate(db.getSession(), user, password, AuthenticationEvent.Method.BASIC); | |||
} | |||
@Test | |||
public void authentication_updates_db_if_PBKDF2_iterations_changes() { | |||
String password = randomAlphanumeric(60); | |||
UserDto user = newUserDto().setLogin("myself"); | |||
db.users().insertUser(user); | |||
underTest.storeHashPassword(user, password); | |||
underTest.authenticate(db.getSession(), user, password, AuthenticationEvent.Method.BASIC); | |||
assertThat(user.getCryptedPassword()).startsWith("1$"); | |||
settings.setProperty("sonar.internal.pbkdf2.iterations", 3); | |||
CredentialsLocalAuthentication underTest = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
underTest.authenticate(db.getSession(), user, password, AuthenticationEvent.Method.BASIC); | |||
assertThat(user.getCryptedPassword()).startsWith("3$"); | |||
underTest.authenticate(db.getSession(), user, password, AuthenticationEvent.Method.BASIC); | |||
} | |||
@Test | |||
public void authentication_with_pbkdf2_with_correct_password_should_work() { | |||
String password = randomAlphanumeric(60); | |||
UserDto user = newUserDto() | |||
.setHashMethod(PBKDF2.name()); | |||
underTest.storeHashPassword(user, password); | |||
assertThat(user.getCryptedPassword()).hasSize(88 + 2); | |||
assertThat(user.getCryptedPassword()).startsWith("1$"); | |||
assertThat(user.getSalt()).hasSize(28); | |||
underTest.authenticate(db.getSession(), user, password, AuthenticationEvent.Method.BASIC); | |||
} | |||
@Test | |||
public void authentication_with_pbkdf2_with_default_number_of_iterations() { | |||
settings.clear(); | |||
CredentialsLocalAuthentication underTest = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
String password = randomAlphanumeric(60); | |||
UserDto user = newUserDto() | |||
.setHashMethod(PBKDF2.name()); | |||
underTest.storeHashPassword(user, password); | |||
assertThat(user.getCryptedPassword()).hasSize(88 + 7); | |||
assertThat(user.getCryptedPassword()).startsWith("100000$"); | |||
assertThat(user.getSalt()).hasSize(28); | |||
underTest.authenticate(db.getSession(), user, password, AuthenticationEvent.Method.BASIC); | |||
} | |||
@Test | |||
public void authentication_with_pbkdf2_with_incorrect_password_should_throw_AuthenticationException() { | |||
UserDto user = newUserDto() | |||
.setHashMethod(PBKDF2.name()) | |||
.setCryptedPassword("1$hash") | |||
.setSalt("salt"); | |||
expectedException.expect(AuthenticationException.class); | |||
expectedException.expectMessage("wrong password"); | |||
underTest.authenticate(db.getSession(), user, "WHATEVER", AuthenticationEvent.Method.BASIC); | |||
} | |||
@Test | |||
public void authentication_with_pbkdf2_with_invalid_password_should_throw_AuthenticationException() { | |||
String password = randomAlphanumeric(60); | |||
byte[] saltRandom = new byte[20]; | |||
RANDOM.nextBytes(saltRandom); | |||
String salt = DigestUtils.sha1Hex(saltRandom); | |||
UserDto user = newUserDto() | |||
.setHashMethod(PBKDF2.name()) | |||
.setCryptedPassword(DigestUtils.sha1Hex("--" + salt + "--" + password + "--")) | |||
.setSalt(salt); | |||
expectedException.expect(AuthenticationException.class); | |||
expectedException.expectMessage("invalid hash stored"); | |||
underTest.authenticate(db.getSession(), user, "WHATEVER", AuthenticationEvent.Method.BASIC); | |||
} | |||
@Test | |||
public void authentication_with_pbkdf2_with_empty_password_should_throw_AuthenticationException() { | |||
byte[] saltRandom = new byte[20]; | |||
RANDOM.nextBytes(saltRandom); | |||
String salt = DigestUtils.sha1Hex(saltRandom); | |||
UserDto user = newUserDto() | |||
.setCryptedPassword(null) | |||
.setHashMethod(PBKDF2.name()) | |||
.setSalt(salt); | |||
expectedException.expect(AuthenticationException.class); | |||
expectedException.expectMessage("null password in DB"); | |||
underTest.authenticate(db.getSession(), user, "WHATEVER", AuthenticationEvent.Method.BASIC); | |||
} | |||
@Test | |||
public void authentication_with_pbkdf2_with_empty_salt_should_throw_AuthenticationException() { | |||
String password = randomAlphanumeric(60); | |||
UserDto user = newUserDto() | |||
.setHashMethod(PBKDF2.name()) | |||
.setCryptedPassword(DigestUtils.sha1Hex("--0242b0b4c0a93ddfe09dd886de50bc25ba000b51--" + password + "--")) | |||
.setSalt(null); | |||
expectedException.expect(AuthenticationException.class); | |||
expectedException.expectMessage("null salt"); | |||
underTest.authenticate(db.getSession(), user, "WHATEVER", AuthenticationEvent.Method.BASIC); | |||
} | |||
} |
@@ -22,6 +22,7 @@ package org.sonar.server.authentication; | |||
import org.junit.After; | |||
import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.sonar.api.config.internal.MapSettings; | |||
import org.sonar.api.notifications.Notification; | |||
import org.sonar.api.utils.log.LogTester; | |||
import org.sonar.api.utils.log.LoggerLevel; | |||
@@ -45,7 +46,8 @@ public class DefaultAdminCredentialsVerifierImplTest { | |||
@Rule | |||
public LogTester logTester = new LogTester(); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final NotificationManager notificationManager = mock(NotificationManager.class); | |||
private final DefaultAdminCredentialsVerifierImpl underTest = new DefaultAdminCredentialsVerifierImpl(db.getDbClient(), localAuthentication, notificationManager); |
@@ -61,7 +61,7 @@ import static org.sonar.server.authentication.event.AuthenticationExceptionMatch | |||
public class HttpHeadersAuthenticationTest { | |||
private final MapSettings settings = new MapSettings(); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
@Rule | |||
public ExpectedException expectedException = none(); | |||
@@ -92,7 +92,7 @@ public class HttpHeadersAuthenticationTest { | |||
private GroupDto sonarUsers; | |||
private final System2 system2 = mock(System2.class); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final UserIndexer userIndexer = new UserIndexer(db.getDbClient(), es.client()); | |||
@@ -67,7 +67,7 @@ public class UserRegistrarImplTest { | |||
.setEnabled(true) | |||
.setAllowsUsersToSignUp(true); | |||
private final MapSettings settings = new MapSettings(); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
@Rule | |||
public ExpectedException expectedException = ExpectedException.none(); | |||
@@ -76,7 +76,7 @@ public class UserRegistrarImplTest { | |||
@Rule | |||
public EsTester es = EsTester.create(); | |||
private final UserIndexer userIndexer = new UserIndexer(db.getDbClient(), es.client()); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final DefaultGroupFinder groupFinder = new DefaultGroupFinder(db.getDbClient()); | |||
private final UserUpdater userUpdater = new UserUpdater( | |||
mock(NewUserNotifier.class), |
@@ -74,8 +74,8 @@ public class UserUpdaterCreateTest { | |||
private final ArgumentCaptor<NewUserHandler.Context> newUserHandler = ArgumentCaptor.forClass(NewUserHandler.Context.class); | |||
private final DbSession session = db.getSession(); | |||
private final UserIndexer userIndexer = new UserIndexer(dbClient, es.client()); | |||
private final MapSettings settings = new MapSettings(); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final UserUpdater underTest = new UserUpdater(newUserNotifier, dbClient, userIndexer, | |||
new DefaultGroupFinder(dbClient), settings.asConfig(), localAuthentication); | |||
@@ -100,8 +100,8 @@ public class UserUpdaterCreateTest { | |||
assertThat(dto.isActive()).isTrue(); | |||
assertThat(dto.isLocal()).isTrue(); | |||
assertThat(dto.getSalt()).isNull(); | |||
assertThat(dto.getHashMethod()).isEqualTo(HashMethod.BCRYPT.name()); | |||
assertThat(dto.getSalt()).isNotNull(); | |||
assertThat(dto.getHashMethod()).isEqualTo(HashMethod.PBKDF2.name()); | |||
assertThat(dto.getCryptedPassword()).isNotNull(); | |||
assertThat(dto.getCreatedAt()) | |||
.isPositive() |
@@ -59,8 +59,8 @@ public class UserUpdaterReactivateTest { | |||
private final NewUserNotifier newUserNotifier = mock(NewUserNotifier.class); | |||
private final DbSession session = db.getSession(); | |||
private final UserIndexer userIndexer = new UserIndexer(dbClient, es.client()); | |||
private final MapSettings settings = new MapSettings(); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final UserUpdater underTest = new UserUpdater(newUserNotifier, dbClient, userIndexer, | |||
new DefaultGroupFinder(dbClient), | |||
settings.asConfig(), localAuthentication); | |||
@@ -86,8 +86,8 @@ public class UserUpdaterReactivateTest { | |||
assertThat(reloaded.getEmail()).isEqualTo("marius2@mail.com"); | |||
assertThat(reloaded.getScmAccounts()).isNull(); | |||
assertThat(reloaded.isLocal()).isTrue(); | |||
assertThat(reloaded.getSalt()).isNull(); | |||
assertThat(reloaded.getHashMethod()).isEqualTo(HashMethod.BCRYPT.name()); | |||
assertThat(reloaded.getSalt()).isNotNull(); | |||
assertThat(reloaded.getHashMethod()).isEqualTo(HashMethod.PBKDF2.name()); | |||
assertThat(reloaded.getCryptedPassword()).isNotNull().isNotEqualTo("650d2261c98361e2f67f90ce5c65a95e7d8ea2fg"); | |||
assertThat(reloaded.getCreatedAt()).isEqualTo(user.getCreatedAt()); | |||
assertThat(reloaded.getUpdatedAt()).isGreaterThan(user.getCreatedAt()); |
@@ -72,8 +72,8 @@ public class UserUpdaterUpdateTest { | |||
private final NewUserNotifier newUserNotifier = mock(NewUserNotifier.class); | |||
private final DbSession session = db.getSession(); | |||
private final UserIndexer userIndexer = new UserIndexer(dbClient, es.client()); | |||
private final MapSettings settings = new MapSettings(); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final UserUpdater underTest = new UserUpdater(newUserNotifier, dbClient, userIndexer, | |||
new DefaultGroupFinder(dbClient), settings.asConfig(), localAuthentication); | |||
@@ -54,8 +54,8 @@ public class ChangePasswordActionTest { | |||
public EsTester es = EsTester.createCustom(UserIndexDefinition.createForTest()); | |||
@Rule | |||
public UserSessionRule userSessionRule = UserSessionRule.standalone().logIn(); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final UserUpdater userUpdater = new UserUpdater(mock(NewUserNotifier.class), db.getDbClient(), | |||
new UserIndexer(db.getDbClient(), es.client()), new DefaultGroupFinder(db.getDbClient()), |
@@ -63,7 +63,7 @@ import static org.sonar.server.user.index.UserIndexDefinition.FIELD_SCM_ACCOUNTS | |||
public class CreateActionTest { | |||
private final MapSettings settings = new MapSettings(); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private final System2 system2 = new AlwaysIncreasingSystem2(); | |||
@Rule | |||
@@ -77,7 +77,7 @@ public class CreateActionTest { | |||
private final UserIndexer userIndexer = new UserIndexer(db.getDbClient(), es.client()); | |||
private GroupDto defaultGroup; | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final WsActionTester tester = new WsActionTester(new CreateAction(db.getDbClient(), new UserUpdater(mock(NewUserNotifier.class), | |||
db.getDbClient(), userIndexer, new DefaultGroupFinder(db.getDbClient()), settings.asConfig(), localAuthentication), userSessionRule)); | |||
@@ -50,7 +50,7 @@ import static org.sonar.db.user.UserTesting.newUserDto; | |||
public class UpdateActionTest { | |||
private final MapSettings settings = new MapSettings(); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private final System2 system2 = new System2(); | |||
@Rule | |||
@@ -65,7 +65,7 @@ public class UpdateActionTest { | |||
private final DbClient dbClient = db.getDbClient(); | |||
private final DbSession dbSession = db.getSession(); | |||
private final UserIndexer userIndexer = new UserIndexer(dbClient, es.client()); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient()); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient(), settings.asConfig()); | |||
private final WsActionTester ws = new WsActionTester(new UpdateAction( | |||
new UserUpdater(mock(NewUserNotifier.class), dbClient, userIndexer, new DefaultGroupFinder(db.getDbClient()), settings.asConfig(), localAuthentication), | |||
userSession, new UserJsonWriter(userSession), dbClient)); |
@@ -62,11 +62,11 @@ public class UpdateIdentityProviderActionTest { | |||
@Rule | |||
public UserSessionRule userSession = UserSessionRule.standalone().logIn().setSystemAdministrator(); | |||
private final MapSettings settings = new MapSettings(); | |||
private final MapSettings settings = new MapSettings().setProperty("sonar.internal.pbkdf2.iterations", "1"); | |||
private final DbClient dbClient = db.getDbClient(); | |||
private final DbSession dbSession = db.getSession(); | |||
private final UserIndexer userIndexer = new UserIndexer(dbClient, es.client()); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(dbClient); | |||
private final CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(dbClient, settings.asConfig()); | |||
private final WsActionTester underTest = new WsActionTester(new UpdateIdentityProviderAction(dbClient, identityProviderRepository, | |||
new UserUpdater(mock(NewUserNotifier.class), dbClient, userIndexer, new DefaultGroupFinder(db.getDbClient()), settings.asConfig(), localAuthentication), |