package org.apereo.cas.util.gen;
import java.security.SecureRandom;
import java.util.stream.IntStream;
/**
* Implementation of the RandomStringGenerator that allows you to define the
* length of the random part.
*
* @author Scott Battaglia
* @since 3.0.0
*/
public class DefaultRandomStringGenerator implements RandomStringGenerator {
/** The default maximum length. */
public static final int DEFAULT_MAX_RANDOM_LENGTH = 35;
/** The array of printable characters to be used in our random string. */
private static final char[] PRINTABLE_CHARACTERS = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ012345679".toCharArray();
/** An instance of secure random to ensure randomness is secure. */
private SecureRandom randomizer = new SecureRandom();
/** The maximum length the random string can be. */
private int maximumRandomLength;
/**
* Instantiates a new default random string generator
* with length set to {@link #DEFAULT_MAX_RANDOM_LENGTH}.
*/
public DefaultRandomStringGenerator() {
this.maximumRandomLength = DEFAULT_MAX_RANDOM_LENGTH;
}
/**
* Instantiates a new default random string generator.
*
* @param maxRandomLength the max random length
*/
public DefaultRandomStringGenerator(final int maxRandomLength) {
this.maximumRandomLength = maxRandomLength;
}
@Override
public int getMinLength() {
return this.maximumRandomLength;
}
@Override
public int getMaxLength() {
return this.maximumRandomLength;
}
@Override
public String getNewString() {
final byte[] random = getNewStringAsBytes();
return convertBytesToString(random);
}
@Override
public byte[] getNewStringAsBytes() {
final byte[] random = new byte[this.maximumRandomLength];
this.randomizer.nextBytes(random);
return random;
}
/**
* Convert bytes to string, taking into account {@link #PRINTABLE_CHARACTERS}.
*
* @param random the random
* @return the string
*/
private static String convertBytesToString(final byte[] random) {
final char[] output = new char[random.length];
IntStream.range(0, random.length).forEach(i -> {
final int index = Math.abs(random[i] % PRINTABLE_CHARACTERS.length);
output[i] = PRINTABLE_CHARACTERS[index];
});
return new String(output);
}
}