diff --git a/core/src/main/java/org/springframework/security/core/token/KeyBasedPersistenceTokenService.java b/core/src/main/java/org/springframework/security/core/token/KeyBasedPersistenceTokenService.java index 8f214b0147a..a1e266cd972 100644 --- a/core/src/main/java/org/springframework/security/core/token/KeyBasedPersistenceTokenService.java +++ b/core/src/main/java/org/springframework/security/core/token/KeyBasedPersistenceTokenService.java @@ -18,11 +18,11 @@ import java.security.SecureRandom; import java.util.Base64; +import java.util.HexFormat; import org.jspecify.annotations.Nullable; import org.springframework.beans.factory.InitializingBean; -import org.springframework.security.crypto.codec.Hex; import org.springframework.security.crypto.codec.Utf8; import org.springframework.util.Assert; import org.springframework.util.StringUtils; @@ -71,6 +71,7 @@ *
* * @author Ben Alex + * @author Andrey Litvitski * */ public class KeyBasedPersistenceTokenService implements TokenService, InitializingBean { @@ -142,7 +143,7 @@ private String computeKey(String serverSecret, String content) { private String generatePseudoRandomNumber() { byte[] randomBytes = new byte[this.pseudoRandomNumberBytes]; this.secureRandom.nextBytes(randomBytes); - return new String(Hex.encode(randomBytes)); + return new String(HexFormat.of().formatHex(randomBytes)); } private String computeServerSecretApplicableAt(long time) { diff --git a/core/src/main/java/org/springframework/security/core/token/Sha512DigestUtils.java b/core/src/main/java/org/springframework/security/core/token/Sha512DigestUtils.java index 5093afe6935..b517424a8b8 100644 --- a/core/src/main/java/org/springframework/security/core/token/Sha512DigestUtils.java +++ b/core/src/main/java/org/springframework/security/core/token/Sha512DigestUtils.java @@ -18,8 +18,7 @@ import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; - -import org.springframework.security.crypto.codec.Hex; +import java.util.HexFormat; /** * Provides SHA512 digest methods. @@ -73,7 +72,7 @@ public static byte[] sha(String data) { * @return SHA digest as a hex string */ public static String shaHex(byte[] data) { - return new String(Hex.encode(sha(data))); + return HexFormat.of().formatHex(sha(data)); } /** @@ -82,7 +81,7 @@ public static String shaHex(byte[] data) { * @return SHA digest as a hex string */ public static String shaHex(String data) { - return new String(Hex.encode(sha(data))); + return HexFormat.of().formatHex(sha(data)); } } diff --git a/crypto/src/main/java/org/springframework/security/crypto/codec/Hex.java b/crypto/src/main/java/org/springframework/security/crypto/codec/Hex.java deleted file mode 100644 index 8ca0b2ad7d0..00000000000 --- a/crypto/src/main/java/org/springframework/security/crypto/codec/Hex.java +++ /dev/null @@ -1,66 +0,0 @@ -/* - * Copyright 2004-present the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * https://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package org.springframework.security.crypto.codec; - -/** - * Hex data encoder. Converts byte arrays (such as those obtained from message digests) - * into hexadecimal string representation. - *
- * For internal use only.
- *
- * @author Luke Taylor
- * @since 3.0
- */
-public final class Hex {
-
- private static final char[] HEX = "0123456789abcdef".toCharArray();
-
- private Hex() {
- }
-
- public static char[] encode(byte[] bytes) {
- final int nBytes = bytes.length;
- char[] result = new char[2 * nBytes];
- int j = 0;
- for (byte aByte : bytes) {
- // Char for top 4 bits
- result[j++] = HEX[(0xF0 & aByte) >>> 4];
- // Bottom 4
- result[j++] = HEX[(0x0F & aByte)];
- }
- return result;
- }
-
- public static byte[] decode(CharSequence s) {
- int nChars = s.length();
- if (nChars % 2 != 0) {
- throw new IllegalArgumentException("Hex-encoded string must have an even number of characters");
- }
- byte[] result = new byte[nChars / 2];
- for (int i = 0; i < nChars; i += 2) {
- int msb = Character.digit(s.charAt(i), 16);
- int lsb = Character.digit(s.charAt(i + 1), 16);
- if (msb < 0 || lsb < 0) {
- throw new IllegalArgumentException(
- "Detected a Non-hex character at " + (i + 1) + " or " + (i + 2) + " position");
- }
- result[i / 2] = (byte) ((msb << 4) | lsb);
- }
- return result;
- }
-
-}
diff --git a/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesBytesEncryptor.java b/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesBytesEncryptor.java
index 5ba1ab5c77a..24a74ea95da 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesBytesEncryptor.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesBytesEncryptor.java
@@ -17,6 +17,7 @@
package org.springframework.security.crypto.encrypt;
import java.security.spec.AlgorithmParameterSpec;
+import java.util.HexFormat;
import javax.crypto.Cipher;
import javax.crypto.SecretKey;
@@ -27,7 +28,6 @@
import org.jspecify.annotations.Nullable;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
import org.springframework.security.crypto.util.EncodingUtils;
@@ -102,7 +102,7 @@ public AesBytesEncryptor(String password, CharSequence salt, @Nullable BytesKeyG
public AesBytesEncryptor(String password, CharSequence salt, @Nullable BytesKeyGenerator ivGenerator,
CipherAlgorithm alg) {
this(CipherUtils.newSecretKey("PBKDF2WithHmacSHA1",
- new PBEKeySpec(password.toCharArray(), Hex.decode(salt), 1024, 256)), ivGenerator, alg);
+ new PBEKeySpec(password.toCharArray(), HexFormat.of().parseHex(salt), 1024, 256)), ivGenerator, alg);
}
/**
diff --git a/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesCbcBytesEncryptor.java b/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesCbcBytesEncryptor.java
index 7cae0f3de78..c40ca51a7bd 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesCbcBytesEncryptor.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesCbcBytesEncryptor.java
@@ -16,6 +16,7 @@
package org.springframework.security.crypto.encrypt;
+import java.util.HexFormat;
import java.util.Objects;
import javax.crypto.Cipher;
@@ -24,7 +25,6 @@
import javax.crypto.spec.PBEKeySpec;
import javax.crypto.spec.SecretKeySpec;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
import org.springframework.security.crypto.util.EncodingUtils;
@@ -119,7 +119,7 @@ public byte[] decrypt(byte[] encryptedBytes) {
private static SecretKey deriveKey(String password, CharSequence salt) {
return CipherUtils.newSecretKey("PBKDF2WithHmacSHA256",
- new PBEKeySpec(password.toCharArray(), Hex.decode(salt), DEFAULT_PBKDF2_ITERATIONS, 256));
+ new PBEKeySpec(password.toCharArray(), HexFormat.of().parseHex(salt), DEFAULT_PBKDF2_ITERATIONS, 256));
}
/**
diff --git a/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesGcmBytesEncryptor.java b/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesGcmBytesEncryptor.java
index 980221cb33c..9ab802eb640 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesGcmBytesEncryptor.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/encrypt/AesGcmBytesEncryptor.java
@@ -16,6 +16,7 @@
package org.springframework.security.crypto.encrypt;
+import java.util.HexFormat;
import java.util.Objects;
import javax.crypto.Cipher;
@@ -24,7 +25,6 @@
import javax.crypto.spec.PBEKeySpec;
import javax.crypto.spec.SecretKeySpec;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
import org.springframework.security.crypto.util.EncodingUtils;
@@ -126,7 +126,7 @@ public byte[] decrypt(byte[] encryptedBytes) {
private static SecretKey deriveKey(String password, CharSequence salt) {
return CipherUtils.newSecretKey("PBKDF2WithHmacSHA256",
- new PBEKeySpec(password.toCharArray(), Hex.decode(salt), DEFAULT_PBKDF2_ITERATIONS, 256));
+ new PBEKeySpec(password.toCharArray(), HexFormat.of().parseHex(salt), DEFAULT_PBKDF2_ITERATIONS, 256));
}
/**
diff --git a/crypto/src/main/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptor.java b/crypto/src/main/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptor.java
index 282a71689b2..85608a2322b 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptor.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptor.java
@@ -16,11 +16,12 @@
package org.springframework.security.crypto.encrypt;
+import java.util.HexFormat;
+
import org.bouncycastle.crypto.PBEParametersGenerator;
import org.bouncycastle.crypto.generators.PKCS5S2ParametersGenerator;
import org.bouncycastle.crypto.params.KeyParameter;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
@@ -47,7 +48,7 @@ abstract class BouncyCastleAesBytesEncryptor implements BytesEncryptor {
this.ivGenerator = ivGenerator;
PBEParametersGenerator keyGenerator = new PKCS5S2ParametersGenerator();
byte[] pkcs12PasswordBytes = PBEParametersGenerator.PKCS5PasswordToUTF8Bytes(password.toCharArray());
- keyGenerator.init(pkcs12PasswordBytes, Hex.decode(salt), 1024);
+ keyGenerator.init(pkcs12PasswordBytes, HexFormat.of().parseHex(salt), 1024);
this.secretKey = (KeyParameter) keyGenerator.generateDerivedParameters(256);
}
diff --git a/crypto/src/main/java/org/springframework/security/crypto/encrypt/HexEncodingTextEncryptor.java b/crypto/src/main/java/org/springframework/security/crypto/encrypt/HexEncodingTextEncryptor.java
index 1a3ead10347..2a0e92726c7 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/encrypt/HexEncodingTextEncryptor.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/encrypt/HexEncodingTextEncryptor.java
@@ -16,7 +16,8 @@
package org.springframework.security.crypto.encrypt;
-import org.springframework.security.crypto.codec.Hex;
+import java.util.HexFormat;
+
import org.springframework.security.crypto.codec.Utf8;
/**
@@ -36,12 +37,12 @@ final class HexEncodingTextEncryptor implements TextEncryptor {
@Override
public String encrypt(String text) {
- return new String(Hex.encode(this.encryptor.encrypt(Utf8.encode(text))));
+ return HexFormat.of().formatHex(this.encryptor.encrypt(Utf8.encode(text)));
}
@Override
public String decrypt(String encryptedText) {
- return Utf8.decode(this.encryptor.decrypt(Hex.decode(encryptedText)));
+ return Utf8.decode(this.encryptor.decrypt(HexFormat.of().parseHex(encryptedText)));
}
}
diff --git a/crypto/src/main/java/org/springframework/security/crypto/encrypt/RsaSecretEncryptor.java b/crypto/src/main/java/org/springframework/security/crypto/encrypt/RsaSecretEncryptor.java
index c6ecab9ac3d..16e8325324e 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/encrypt/RsaSecretEncryptor.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/encrypt/RsaSecretEncryptor.java
@@ -25,12 +25,12 @@
import java.security.PublicKey;
import java.security.interfaces.RSAPublicKey;
import java.util.Base64;
+import java.util.HexFormat;
import javax.crypto.Cipher;
import org.jspecify.annotations.Nullable;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.KeyGenerators;
/**
@@ -138,7 +138,7 @@ public RsaSecretEncryptor(String encoding, PublicKey publicKey, @Nullable Privat
this.privateKey = privateKey;
this.defaultCharset = Charset.forName(DEFAULT_ENCODING);
this.algorithm = algorithm;
- this.salt = isHex(salt) ? salt : new String(Hex.encode(salt.getBytes(this.defaultCharset)));
+ this.salt = isHex(salt) ? salt : HexFormat.of().formatHex(salt.getBytes(this.defaultCharset));
this.gcm = gcm;
}
@@ -176,8 +176,8 @@ public byte[] decrypt(byte[] encryptedByteArray) {
private static byte[] encrypt(byte[] text, PublicKey key, RsaAlgorithm alg, String salt, boolean gcm) {
byte[] random = KeyGenerators.secureRandom(16).generateKey();
- BytesEncryptor aes = gcm ? Encryptors.stronger(new String(Hex.encode(random)), salt)
- : Encryptors.standard(new String(Hex.encode(random)), salt);
+ BytesEncryptor aes = gcm ? Encryptors.stronger(HexFormat.of().formatHex(random), salt)
+ : Encryptors.standard(HexFormat.of().formatHex(random), salt);
try {
final Cipher cipher = Cipher.getInstance(alg.getJceName());
cipher.init(Cipher.ENCRYPT_MODE, key);
@@ -218,7 +218,7 @@ private static byte[] decrypt(byte[] text, @Nullable PrivateKey key, RsaAlgorith
input.read(random);
final Cipher cipher = Cipher.getInstance(alg.getJceName());
cipher.init(Cipher.DECRYPT_MODE, key);
- String secret = new String(Hex.encode(cipher.doFinal(random)));
+ String secret = HexFormat.of().formatHex(cipher.doFinal(random));
byte[] buffer = new byte[text.length - random.length - 2];
input.read(buffer);
BytesEncryptor aes = gcm ? Encryptors.stronger(secret, salt) : Encryptors.standard(secret, salt);
@@ -235,7 +235,7 @@ private static byte[] decrypt(byte[] text, @Nullable PrivateKey key, RsaAlgorith
private static boolean isHex(String input) {
try {
- Hex.decode(input);
+ HexFormat.of().parseHex(input);
return true;
}
catch (Exception ex) {
diff --git a/crypto/src/main/java/org/springframework/security/crypto/keygen/HexEncodingStringKeyGenerator.java b/crypto/src/main/java/org/springframework/security/crypto/keygen/HexEncodingStringKeyGenerator.java
index f6f9a22f939..00a70181331 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/keygen/HexEncodingStringKeyGenerator.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/keygen/HexEncodingStringKeyGenerator.java
@@ -16,7 +16,7 @@
package org.springframework.security.crypto.keygen;
-import org.springframework.security.crypto.codec.Hex;
+import java.util.HexFormat;
/**
* A StringKeyGenerator that generates hex-encoded String keys. Delegates to a
@@ -34,7 +34,7 @@ final class HexEncodingStringKeyGenerator implements StringKeyGenerator {
@Override
public String generateKey() {
- return new String(Hex.encode(this.keyGenerator.generateKey()));
+ return HexFormat.of().formatHex(this.keyGenerator.generateKey());
}
}
diff --git a/crypto/src/main/java/org/springframework/security/crypto/password/AbstractPasswordEncoder.java b/crypto/src/main/java/org/springframework/security/crypto/password/AbstractPasswordEncoder.java
index 973a11dd550..97186fc7e21 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/password/AbstractPasswordEncoder.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/password/AbstractPasswordEncoder.java
@@ -17,8 +17,8 @@
package org.springframework.security.crypto.password;
import java.security.MessageDigest;
+import java.util.HexFormat;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
import org.springframework.security.crypto.util.EncodingUtils;
@@ -40,12 +40,12 @@ protected AbstractPasswordEncoder() {
protected String encodeNonNullPassword(String rawPassword) {
byte[] salt = this.saltGenerator.generateKey();
byte[] encoded = encodeAndConcatenate(rawPassword, salt);
- return String.valueOf(Hex.encode(encoded));
+ return String.valueOf(HexFormat.of().formatHex(encoded));
}
@Override
protected boolean matchesNonNull(String rawPassword, String encodedPassword) {
- byte[] digested = Hex.decode(encodedPassword);
+ byte[] digested = HexFormat.of().parseHex(encodedPassword);
byte[] salt = EncodingUtils.subArray(digested, 0, this.saltGenerator.getKeyLength());
return matchesNonNull(digested, encodeAndConcatenate(rawPassword, salt));
}
diff --git a/crypto/src/main/java/org/springframework/security/crypto/password/Md4PasswordEncoder.java b/crypto/src/main/java/org/springframework/security/crypto/password/Md4PasswordEncoder.java
index 0ab6b9001ad..6556940f0e6 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/password/Md4PasswordEncoder.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/password/Md4PasswordEncoder.java
@@ -17,8 +17,8 @@
package org.springframework.security.crypto.password;
import java.util.Base64;
+import java.util.HexFormat;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.codec.Utf8;
import org.springframework.security.crypto.keygen.Base64StringKeyGenerator;
import org.springframework.security.crypto.keygen.StringKeyGenerator;
@@ -122,7 +122,7 @@ private String encodedNonNullPassword(byte[] digest) {
if (this.encodeHashAsBase64) {
return Utf8.decode(Base64.getEncoder().encode(digest));
}
- return new String(Hex.encode(digest));
+ return HexFormat.of().formatHex(digest);
}
/**
diff --git a/crypto/src/main/java/org/springframework/security/crypto/password/MessageDigestPasswordEncoder.java b/crypto/src/main/java/org/springframework/security/crypto/password/MessageDigestPasswordEncoder.java
index d899593007a..a8f9fce3e19 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/password/MessageDigestPasswordEncoder.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/password/MessageDigestPasswordEncoder.java
@@ -18,8 +18,8 @@
import java.security.MessageDigest;
import java.util.Base64;
+import java.util.HexFormat;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.codec.Utf8;
import org.springframework.security.crypto.keygen.Base64StringKeyGenerator;
import org.springframework.security.crypto.keygen.StringKeyGenerator;
@@ -132,7 +132,7 @@ private String encodedNonNullPassword(byte[] digest) {
if (this.encodeHashAsBase64) {
return Utf8.decode(Base64.getEncoder().encode(digest));
}
- return new String(Hex.encode(digest));
+ return HexFormat.of().formatHex(digest);
}
/**
diff --git a/crypto/src/main/java/org/springframework/security/crypto/password/Pbkdf2PasswordEncoder.java b/crypto/src/main/java/org/springframework/security/crypto/password/Pbkdf2PasswordEncoder.java
index d456c962674..1f1eb772886 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/password/Pbkdf2PasswordEncoder.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/password/Pbkdf2PasswordEncoder.java
@@ -20,11 +20,11 @@
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Base64;
+import java.util.HexFormat;
import javax.crypto.SecretKeyFactory;
import javax.crypto.spec.PBEKeySpec;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.codec.Utf8;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
@@ -204,7 +204,7 @@ private String encodedNonNullPassword(byte[] bytes) {
if (this.encodeHashAsBase64) {
return Base64.getEncoder().encodeToString(bytes);
}
- return String.valueOf(Hex.encode(bytes));
+ return String.valueOf(HexFormat.of().formatHex(bytes));
}
@Override
@@ -218,7 +218,7 @@ private byte[] decode(String encodedBytes) {
if (this.encodeHashAsBase64) {
return Base64.getDecoder().decode(encodedBytes);
}
- return Hex.decode(encodedBytes);
+ return HexFormat.of().parseHex(encodedBytes);
}
private byte[] encodedNonNullPassword(CharSequence rawPassword, byte[] salt) {
diff --git a/crypto/src/main/java/org/springframework/security/crypto/password/StandardPasswordEncoder.java b/crypto/src/main/java/org/springframework/security/crypto/password/StandardPasswordEncoder.java
index a89641be6c2..6b5b8e37abf 100644
--- a/crypto/src/main/java/org/springframework/security/crypto/password/StandardPasswordEncoder.java
+++ b/crypto/src/main/java/org/springframework/security/crypto/password/StandardPasswordEncoder.java
@@ -17,8 +17,8 @@
package org.springframework.security.crypto.password;
import java.security.MessageDigest;
+import java.util.HexFormat;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.codec.Utf8;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
@@ -94,7 +94,7 @@ private StandardPasswordEncoder(String algorithm, CharSequence secret) {
private String encodedNonNullPassword(CharSequence rawPassword, byte[] salt) {
byte[] digest = digest(rawPassword, salt);
- return new String(Hex.encode(digest));
+ return HexFormat.of().formatHex(digest);
}
private byte[] digest(CharSequence rawPassword, byte[] salt) {
@@ -103,7 +103,7 @@ private byte[] digest(CharSequence rawPassword, byte[] salt) {
}
private byte[] decode(CharSequence encodedPassword) {
- return Hex.decode(encodedPassword);
+ return HexFormat.of().parseHex(encodedPassword);
}
}
diff --git a/crypto/src/test/java/org/springframework/security/crypto/codec/HexTests.java b/crypto/src/test/java/org/springframework/security/crypto/codec/HexTests.java
deleted file mode 100644
index 322d315e27e..00000000000
--- a/crypto/src/test/java/org/springframework/security/crypto/codec/HexTests.java
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright 2004-present the original author or authors.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * https://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.springframework.security.crypto.codec;
-
-import org.junit.jupiter.api.Test;
-
-import static org.assertj.core.api.Assertions.assertThat;
-import static org.assertj.core.api.Assertions.assertThatIllegalArgumentException;
-
-/**
- * Test cases for {@link Hex}.
- *
- * @author Kazuki Shimizu
- */
-public class HexTests {
-
- @Test
- public void encode() {
- assertThat(Hex.encode(new byte[] { (byte) 'A', (byte) 'B', (byte) 'C', (byte) 'D' }))
- .isEqualTo(new char[] { '4', '1', '4', '2', '4', '3', '4', '4' });
- }
-
- @Test
- public void encodeEmptyByteArray() {
- assertThat(Hex.encode(new byte[] {})).isEmpty();
- }
-
- @Test
- public void decode() {
- assertThat(Hex.decode("41424344")).isEqualTo(new byte[] { (byte) 'A', (byte) 'B', (byte) 'C', (byte) 'D' });
- }
-
- @Test
- public void decodeEmptyString() {
- assertThat(Hex.decode("")).isEmpty();
- }
-
- @Test
- public void decodeNotEven() {
- assertThatIllegalArgumentException().isThrownBy(() -> Hex.decode("414243444"))
- .withMessage("Hex-encoded string must have an even number of characters");
- }
-
- @Test
- public void decodeExistNonHexCharAtFirst() {
- assertThatIllegalArgumentException().isThrownBy(() -> Hex.decode("G0"))
- .withMessage("Detected a Non-hex character at 1 or 2 position");
- }
-
- @Test
- public void decodeExistNonHexCharAtSecond() {
- assertThatIllegalArgumentException().isThrownBy(() -> Hex.decode("410G"))
- .withMessage("Detected a Non-hex character at 3 or 4 position");
- }
-
- @Test
- public void decodeExistNonHexCharAtBoth() {
- assertThatIllegalArgumentException().isThrownBy(() -> Hex.decode("4142GG"))
- .withMessage("Detected a Non-hex character at 5 or 6 position");
- }
-
-}
diff --git a/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesBytesEncryptorTests.java b/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesBytesEncryptorTests.java
index f52264acd07..d4cae59d98c 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesBytesEncryptorTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesBytesEncryptorTests.java
@@ -16,13 +16,14 @@
package org.springframework.security.crypto.encrypt;
+import java.util.HexFormat;
+
import javax.crypto.SecretKey;
import javax.crypto.spec.PBEKeySpec;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.encrypt.AesBytesEncryptor.CipherAlgorithm;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.password.Pbkdf2PasswordEncoder.SecretKeyFactoryAlgorithm;
@@ -47,7 +48,7 @@ public class AesBytesEncryptorTests {
@BeforeEach
public void setUp() {
this.generator = mock(BytesKeyGenerator.class);
- given(this.generator.generateKey()).willReturn(Hex.decode("4b0febebd439db7ca77153cb254520c3"));
+ given(this.generator.generateKey()).willReturn(HexFormat.of().parseHex("4b0febebd439db7ca77153cb254520c3"));
given(this.generator.getKeyLength()).willReturn(16);
}
@@ -65,7 +66,7 @@ public void roundtripWhenUsingDefaultCipherThenEncryptsAndDecrypts() {
CryptoAssumptions.assumeCBCJCE();
AesBytesEncryptor encryptor = new AesBytesEncryptor(this.password, this.hexSalt, this.generator);
byte[] encryption = encryptor.encrypt(this.secret.getBytes());
- assertThat(new String(Hex.encode(encryption)))
+ assertThat(new String(HexFormat.of().formatHex(encryption)))
.isEqualTo("4b0febebd439db7ca77153cb254520c3b7232ac29355d07869433f1ecf55fe94");
byte[] decryption = encryptor.decrypt(encryption);
assertThat(new String(decryption)).isEqualTo(this.secret);
@@ -77,7 +78,7 @@ public void roundtripWhenUsingGcmThenEncryptsAndDecrypts() {
AesBytesEncryptor encryptor = new AesBytesEncryptor(this.password, this.hexSalt, this.generator,
CipherAlgorithm.GCM);
byte[] encryption = encryptor.encrypt(this.secret.getBytes());
- assertThat(new String(Hex.encode(encryption)))
+ assertThat(new String(HexFormat.of().formatHex(encryption)))
.isEqualTo("4b0febebd439db7ca77153cb254520c3e4d61ae38207b4e42b820d311dc3d4e0e2f37ed5ee");
byte[] decryption = encryptor.decrypt(encryption);
assertThat(new String(decryption)).isEqualTo(this.secret);
@@ -86,11 +87,12 @@ public void roundtripWhenUsingGcmThenEncryptsAndDecrypts() {
@Test
public void roundtripWhenUsingSecretKeyThenEncryptsAndDecrypts() {
CryptoAssumptions.assumeGCMJCE();
- PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), Hex.decode(this.hexSalt), 1024, 256);
+ PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), HexFormat.of().parseHex(this.hexSalt), 1024,
+ 256);
SecretKey secretKey = CipherUtils.newSecretKey(SecretKeyFactoryAlgorithm.PBKDF2WithHmacSHA1.name(), keySpec);
AesBytesEncryptor encryptor = new AesBytesEncryptor(secretKey, this.generator, CipherAlgorithm.GCM);
byte[] encryption = encryptor.encrypt(this.secret.getBytes());
- assertThat(new String(Hex.encode(encryption)))
+ assertThat(new String(HexFormat.of().formatHex(encryption)))
.isEqualTo("4b0febebd439db7ca77153cb254520c3e4d61ae38207b4e42b820d311dc3d4e0e2f37ed5ee");
byte[] decryption = encryptor.decrypt(encryption);
assertThat(new String(decryption)).isEqualTo(this.secret);
diff --git a/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesCbcBytesEncryptorTests.java b/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesCbcBytesEncryptorTests.java
index dfa187783d2..b35ec426f0d 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesCbcBytesEncryptorTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesCbcBytesEncryptorTests.java
@@ -17,13 +17,13 @@
package org.springframework.security.crypto.encrypt;
import java.nio.charset.StandardCharsets;
+import java.util.HexFormat;
import javax.crypto.SecretKey;
import javax.crypto.spec.PBEKeySpec;
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
import org.springframework.security.crypto.password.Pbkdf2PasswordEncoder.SecretKeyFactoryAlgorithm;
@@ -56,7 +56,8 @@ void roundtripWhenUsingPasswordAndSaltThenEncryptsAndDecrypts() {
@Test
void roundtripWhenUsingSecretKeyThenEncryptsAndDecrypts() {
CryptoAssumptions.assumeCBCJCE();
- PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), Hex.decode(this.hexSalt), 1024, 256);
+ PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), HexFormat.of().parseHex(this.hexSalt), 1024,
+ 256);
SecretKey secretKey = CipherUtils.newSecretKey(SecretKeyFactoryAlgorithm.PBKDF2WithHmacSHA1.name(), keySpec);
AesCbcBytesEncryptor encryptor = AesCbcBytesEncryptor.withSecretKey(secretKey).build();
byte[] encrypted = encryptor.encrypt(this.secret.getBytes());
@@ -67,13 +68,14 @@ void roundtripWhenUsingSecretKeyThenEncryptsAndDecrypts() {
void encryptWhenUsingMockIvThenProducesKnownCiphertext() {
CryptoAssumptions.assumeCBCJCE();
BytesKeyGenerator mockGenerator = mock(BytesKeyGenerator.class);
- given(mockGenerator.generateKey()).willReturn(Hex.decode("4b0febebd439db7ca77153cb254520c3"));
+ given(mockGenerator.generateKey()).willReturn(HexFormat.of().parseHex("4b0febebd439db7ca77153cb254520c3"));
given(mockGenerator.getKeyLength()).willReturn(16);
AesCbcBytesEncryptor encryptor = AesCbcBytesEncryptor.withPassword(this.password, this.hexSalt)
.ivGenerator(mockGenerator)
.build();
byte[] encrypted = encryptor.encrypt(this.secret.getBytes());
- assertThat(Hex.encode(encrypted)).isEqualTo("4b0febebd439db7ca77153cb254520c3b7232ac29355d07869433f1ecf55fe94");
+ assertThat(HexFormat.of().formatHex(encrypted))
+ .isEqualTo("4b0febebd439db7ca77153cb254520c3b7232ac29355d07869433f1ecf55fe94");
assertThat(new String(encryptor.decrypt(encrypted))).isEqualTo(this.secret);
}
@@ -112,7 +114,8 @@ void migratesFromDeprecatedNullIvCbcToAesCbcBytesEncryptor() {
@SuppressWarnings("deprecation")
void withSecretWhenAesBytesEncryptorEncryptsThenDecrypts() {
CryptoAssumptions.assumeCBCJCE();
- PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), Hex.decode(this.hexSalt), 1024, 256);
+ PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), HexFormat.of().parseHex(this.hexSalt), 1024,
+ 256);
SecretKey key = CipherUtils.newSecretKey(SecretKeyFactoryAlgorithm.PBKDF2WithHmacSHA1.name(), keySpec);
AesBytesEncryptor deprecated = new AesBytesEncryptor(key, KeyGenerators.secureRandom(16),
AesBytesEncryptor.CipherAlgorithm.CBC);
@@ -125,7 +128,8 @@ void withSecretWhenAesBytesEncryptorEncryptsThenDecrypts() {
@SuppressWarnings("deprecation")
void aesBytesEncryptorWhenEncryptsThenAesCbcBytesEncryptorDecrypts() {
CryptoAssumptions.assumeCBCJCE();
- PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), Hex.decode(this.hexSalt), 1024, 256);
+ PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), HexFormat.of().parseHex(this.hexSalt), 1024,
+ 256);
SecretKey key = CipherUtils.newSecretKey(SecretKeyFactoryAlgorithm.PBKDF2WithHmacSHA1.name(), keySpec);
AesCbcBytesEncryptor encryptor = AesCbcBytesEncryptor.withSecretKey(key).build();
AesBytesEncryptor deprecated = new AesBytesEncryptor(key, KeyGenerators.secureRandom(16),
@@ -138,7 +142,7 @@ void aesBytesEncryptorWhenEncryptsThenAesCbcBytesEncryptorDecrypts() {
void roundtripWhenUsingCustomIvGeneratorThenEncryptsAndDecrypts() {
CryptoAssumptions.assumeCBCJCE();
BytesKeyGenerator customIvGenerator = mock(BytesKeyGenerator.class);
- given(customIvGenerator.generateKey()).willReturn(Hex.decode("4b0febebd439db7ca77153cb254520c3"));
+ given(customIvGenerator.generateKey()).willReturn(HexFormat.of().parseHex("4b0febebd439db7ca77153cb254520c3"));
given(customIvGenerator.getKeyLength()).willReturn(16);
AesCbcBytesEncryptor encryptor = AesCbcBytesEncryptor.withPassword(this.password, this.hexSalt)
.ivGenerator(customIvGenerator)
diff --git a/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesGcmBytesEncryptorTests.java b/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesGcmBytesEncryptorTests.java
index 62f52bdcf1c..0813f1ef758 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesGcmBytesEncryptorTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/encrypt/AesGcmBytesEncryptorTests.java
@@ -16,12 +16,13 @@
package org.springframework.security.crypto.encrypt;
+import java.util.HexFormat;
+
import javax.crypto.SecretKey;
import javax.crypto.spec.PBEKeySpec;
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
import org.springframework.security.crypto.password.Pbkdf2PasswordEncoder.SecretKeyFactoryAlgorithm;
@@ -53,7 +54,8 @@ void roundtripWhenUsingPasswordAndSaltThenEncryptsAndDecrypts() {
@Test
void roundtripWhenUsingSecretKeyThenEncryptsAndDecrypts() {
CryptoAssumptions.assumeGCMJCE();
- PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), Hex.decode(this.hexSalt), 1024, 256);
+ PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), HexFormat.of().parseHex(this.hexSalt), 1024,
+ 256);
SecretKey secretKey = CipherUtils.newSecretKey(SecretKeyFactoryAlgorithm.PBKDF2WithHmacSHA1.name(), keySpec);
AesGcmBytesEncryptor encryptor = AesGcmBytesEncryptor.withSecretKey(secretKey).build();
byte[] encrypted = encryptor.encrypt(this.secret.getBytes());
@@ -64,13 +66,13 @@ void roundtripWhenUsingSecretKeyThenEncryptsAndDecrypts() {
void encryptWhenUsingMockIvThenProducesKnownCiphertext() {
CryptoAssumptions.assumeGCMJCE();
BytesKeyGenerator mockGenerator = mock(BytesKeyGenerator.class);
- given(mockGenerator.generateKey()).willReturn(Hex.decode("4b0febebd439db7ca77153cb254520c3"));
+ given(mockGenerator.generateKey()).willReturn(HexFormat.of().parseHex("4b0febebd439db7ca77153cb254520c3"));
given(mockGenerator.getKeyLength()).willReturn(16);
AesGcmBytesEncryptor encryptor = AesGcmBytesEncryptor.withPassword(this.password, this.hexSalt)
.ivGenerator(mockGenerator)
.build();
byte[] encrypted = encryptor.encrypt(this.secret.getBytes());
- assertThat(Hex.encode(encrypted))
+ assertThat(HexFormat.of().formatHex(encrypted))
.isEqualTo("4b0febebd439db7ca77153cb254520c3e4d61ae38207b4e42b820d311dc3d4e0e2f37ed5ee");
assertThat(new String(encryptor.decrypt(encrypted))).isEqualTo(this.secret);
}
@@ -89,7 +91,8 @@ void encryptProducesUniqueOutputAndIvIsPrepended() {
@SuppressWarnings("deprecation")
void withSecretWhenAesBytesEncryptorEncryptsThenDecrypts() {
CryptoAssumptions.assumeGCMJCE();
- PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), Hex.decode(this.hexSalt), 1024, 256);
+ PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), HexFormat.of().parseHex(this.hexSalt), 1024,
+ 256);
SecretKey key = CipherUtils.newSecretKey(SecretKeyFactoryAlgorithm.PBKDF2WithHmacSHA1.name(), keySpec);
AesBytesEncryptor deprecated = new AesBytesEncryptor(key, KeyGenerators.secureRandom(16),
AesBytesEncryptor.CipherAlgorithm.GCM);
@@ -102,7 +105,8 @@ void withSecretWhenAesBytesEncryptorEncryptsThenDecrypts() {
@SuppressWarnings("deprecation")
void aesBytesEncryptorWhenEncryptsThenAesGcmBytesEncryptorDecrypts() {
CryptoAssumptions.assumeGCMJCE();
- PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), Hex.decode(this.hexSalt), 1024, 256);
+ PBEKeySpec keySpec = new PBEKeySpec(this.password.toCharArray(), HexFormat.of().parseHex(this.hexSalt), 1024,
+ 256);
SecretKey key = CipherUtils.newSecretKey(SecretKeyFactoryAlgorithm.PBKDF2WithHmacSHA1.name(), keySpec);
AesGcmBytesEncryptor encryptor = AesGcmBytesEncryptor.withSecretKey(key)
.ivGenerator(KeyGenerators.secureRandom(12))
diff --git a/crypto/src/test/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptorEquivalencyTests.java b/crypto/src/test/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptorEquivalencyTests.java
index b2698e97f22..5d0a4cb716c 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptorEquivalencyTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptorEquivalencyTests.java
@@ -19,13 +19,13 @@
import java.security.SecureRandom;
import java.time.Duration;
import java.time.temporal.ChronoUnit;
+import java.util.HexFormat;
import java.util.Random;
import java.util.UUID;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.encrypt.AesBytesEncryptor.CipherAlgorithm;
import org.springframework.security.crypto.keygen.BytesKeyGenerator;
import org.springframework.security.crypto.keygen.KeyGenerators;
@@ -49,7 +49,7 @@ public void setup() {
/** insecure salt byte, recommend 64 or larger than 64 */
byte[] saltBytes = new byte[16];
this.secureRandom.nextBytes(saltBytes);
- this.salt = new String(Hex.encode(saltBytes));
+ this.salt = HexFormat.of().formatHex(saltBytes);
}
@Test
diff --git a/crypto/src/test/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptorTests.java b/crypto/src/test/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptorTests.java
index ee423ff5985..fa8af5a59a6 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptorTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptorTests.java
@@ -17,13 +17,13 @@
package org.springframework.security.crypto.encrypt;
import java.security.SecureRandom;
+import java.util.HexFormat;
import java.util.UUID;
import org.bouncycastle.util.Arrays;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.KeyGenerators;
import static org.assertj.core.api.Assertions.assertThat;
@@ -44,7 +44,7 @@ public void setup() {
this.password = UUID.randomUUID().toString();
byte[] saltBytes = new byte[16];
secureRandom.nextBytes(saltBytes);
- this.salt = new String(Hex.encode(saltBytes));
+ this.salt = HexFormat.of().formatHex(saltBytes);
this.testData = new byte[1024 * 1024];
secureRandom.nextBytes(this.testData);
}
diff --git a/crypto/src/test/java/org/springframework/security/crypto/keygen/KeyGeneratorsTests.java b/crypto/src/test/java/org/springframework/security/crypto/keygen/KeyGeneratorsTests.java
index 8413bf1b9c9..4b9c4cbfbf3 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/keygen/KeyGeneratorsTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/keygen/KeyGeneratorsTests.java
@@ -17,11 +17,10 @@
package org.springframework.security.crypto.keygen;
import java.util.Arrays;
+import java.util.HexFormat;
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
-
import static org.assertj.core.api.Assertions.assertThat;
public class KeyGeneratorsTests {
@@ -61,7 +60,7 @@ public void string() {
StringKeyGenerator keyGenerator = KeyGenerators.string();
String hexStringKey = keyGenerator.generateKey();
assertThat(hexStringKey).hasSize(16);
- assertThat(Hex.decode(hexStringKey)).hasSize(8);
+ assertThat(HexFormat.of().parseHex(hexStringKey)).hasSize(8);
String hexStringKey2 = keyGenerator.generateKey();
assertThat(hexStringKey.equals(hexStringKey2)).isFalse();
}
diff --git a/crypto/src/test/java/org/springframework/security/crypto/password/DigesterTests.java b/crypto/src/test/java/org/springframework/security/crypto/password/DigesterTests.java
index d70ce8cb94a..e48de9d8ea6 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/password/DigesterTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/password/DigesterTests.java
@@ -16,9 +16,10 @@
package org.springframework.security.crypto.password;
+import java.util.HexFormat;
+
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.codec.Utf8;
import static org.assertj.core.api.Assertions.assertThat;
@@ -30,7 +31,7 @@ public void digestIsCorrectFor3Iterations() {
Digester digester = new Digester("SHA-1", 3);
byte[] result = digester.digest(Utf8.encode("text"));
// echo -n text | openssl sha1 -binary | openssl sha1 -binary | openssl sha1
- assertThat(new String(Hex.encode(result))).isEqualTo("3cfa28da425eca5b894f0af2b158adf7001e000f");
+ assertThat(HexFormat.of().formatHex(result)).isEqualTo("3cfa28da425eca5b894f0af2b158adf7001e000f");
}
}
diff --git a/crypto/src/test/java/org/springframework/security/crypto/password/Pbkdf2PasswordEncoderTests.java b/crypto/src/test/java/org/springframework/security/crypto/password/Pbkdf2PasswordEncoderTests.java
index 2331f257092..570caa5b302 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/password/Pbkdf2PasswordEncoderTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/password/Pbkdf2PasswordEncoderTests.java
@@ -17,10 +17,10 @@
package org.springframework.security.crypto.password;
import java.util.Arrays;
+import java.util.HexFormat;
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.crypto.keygen.KeyGenerators;
import static org.assertj.core.api.Assertions.assertThat;
@@ -116,9 +116,9 @@ public void migrate() {
final int saltLength = KeyGenerators.secureRandom().getKeyLength();
String encodedPassword = "ab1146a8458d4ce4e65789e5a3f60e423373cfa10b01abd23739e5ae2fdc37f8e9ede4ae6da65264";
String originalEncodedPassword = "ab1146a8458d4ce4ab1146a8458d4ce4e65789e5a3f60e423373cfa10b01abd23739e5ae2fdc37f8e9ede4ae6da65264";
- byte[] originalBytes = Hex.decode(originalEncodedPassword);
+ byte[] originalBytes = HexFormat.of().parseHex(originalEncodedPassword);
byte[] fixedBytes = Arrays.copyOfRange(originalBytes, saltLength, originalBytes.length);
- String fixedHex = String.valueOf(Hex.encode(fixedBytes));
+ String fixedHex = String.valueOf(HexFormat.of().formatHex(fixedBytes));
assertThat(fixedHex).isEqualTo(encodedPassword);
}
diff --git a/crypto/src/test/java/org/springframework/security/crypto/util/EncodingUtilsTests.java b/crypto/src/test/java/org/springframework/security/crypto/util/EncodingUtilsTests.java
index 2cae0df7896..f08e648a0bc 100644
--- a/crypto/src/test/java/org/springframework/security/crypto/util/EncodingUtilsTests.java
+++ b/crypto/src/test/java/org/springframework/security/crypto/util/EncodingUtilsTests.java
@@ -17,11 +17,10 @@
package org.springframework.security.crypto.util;
import java.util.Arrays;
+import java.util.HexFormat;
import org.junit.jupiter.api.Test;
-import org.springframework.security.crypto.codec.Hex;
-
import static org.assertj.core.api.Assertions.assertThat;
public class EncodingUtilsTests {
@@ -30,7 +29,7 @@ public class EncodingUtilsTests {
public void hexEncode() {
byte[] bytes = new byte[] { (byte) 0x01, (byte) 0xFF, (byte) 65, (byte) 66, (byte) 67, (byte) 0xC0, (byte) 0xC1,
(byte) 0xC2 };
- String result = new String(Hex.encode(bytes));
+ String result = HexFormat.of().formatHex(bytes);
assertThat(result).isEqualTo("01ff414243c0c1c2");
}
@@ -38,7 +37,7 @@ public void hexEncode() {
public void hexDecode() {
byte[] bytes = new byte[] { (byte) 0x01, (byte) 0xFF, (byte) 65, (byte) 66, (byte) 67, (byte) 0xC0, (byte) 0xC1,
(byte) 0xC2 };
- byte[] result = Hex.decode("01ff414243c0c1c2");
+ byte[] result = HexFormat.of().parseHex("01ff414243c0c1c2");
assertThat(Arrays.equals(bytes, result)).isTrue();
}
diff --git a/oauth2/oauth2-authorization-server/src/test/java/org/springframework/security/oauth2/server/authorization/web/OAuth2ClientAuthenticationFilterTests.java b/oauth2/oauth2-authorization-server/src/test/java/org/springframework/security/oauth2/server/authorization/web/OAuth2ClientAuthenticationFilterTests.java
index 9e9eaf0047b..947c9a36f9b 100644
--- a/oauth2/oauth2-authorization-server/src/test/java/org/springframework/security/oauth2/server/authorization/web/OAuth2ClientAuthenticationFilterTests.java
+++ b/oauth2/oauth2-authorization-server/src/test/java/org/springframework/security/oauth2/server/authorization/web/OAuth2ClientAuthenticationFilterTests.java
@@ -17,6 +17,7 @@
package org.springframework.security.oauth2.server.authorization.web;
import java.nio.charset.StandardCharsets;
+import java.util.HexFormat;
import jakarta.servlet.FilterChain;
import jakarta.servlet.http.HttpServletRequest;
@@ -36,7 +37,6 @@
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.security.oauth2.core.ClientAuthenticationMethod;
import org.springframework.security.oauth2.core.OAuth2AuthenticationException;
import org.springframework.security.oauth2.core.OAuth2Error;
@@ -180,19 +180,19 @@ public void doFilterWhenRequestMatchesAndInvalidCredentialsThenInvalidRequestErr
public void doFilterWhenRequestMatchesAndClientIdContainsNonPrintableASCIIThenInvalidRequestError()
throws Exception {
// Hex 00 -> null
- String clientId = new String(Hex.decode("00"), StandardCharsets.UTF_8);
+ String clientId = new String(HexFormat.of().parseHex("00"), StandardCharsets.UTF_8);
assertWhenInvalidClientIdThenInvalidRequestError(clientId);
// Hex 0a61 -> line feed + a
- clientId = new String(Hex.decode("0a61"), StandardCharsets.UTF_8);
+ clientId = new String(HexFormat.of().parseHex("0a61"), StandardCharsets.UTF_8);
assertWhenInvalidClientIdThenInvalidRequestError(clientId);
// Hex 1b -> escape
- clientId = new String(Hex.decode("1b"), StandardCharsets.UTF_8);
+ clientId = new String(HexFormat.of().parseHex("1b"), StandardCharsets.UTF_8);
assertWhenInvalidClientIdThenInvalidRequestError(clientId);
// Hex 1b61 -> escape + a
- clientId = new String(Hex.decode("1b61"), StandardCharsets.UTF_8);
+ clientId = new String(HexFormat.of().parseHex("1b61"), StandardCharsets.UTF_8);
assertWhenInvalidClientIdThenInvalidRequestError(clientId);
}
diff --git a/web/src/main/java/org/springframework/security/web/authentication/password/HaveIBeenPwnedRestApiPasswordChecker.java b/web/src/main/java/org/springframework/security/web/authentication/password/HaveIBeenPwnedRestApiPasswordChecker.java
index cd892c8d968..6b31b53f1de 100644
--- a/web/src/main/java/org/springframework/security/web/authentication/password/HaveIBeenPwnedRestApiPasswordChecker.java
+++ b/web/src/main/java/org/springframework/security/web/authentication/password/HaveIBeenPwnedRestApiPasswordChecker.java
@@ -20,6 +20,7 @@
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Collections;
+import java.util.HexFormat;
import java.util.List;
import java.util.Locale;
@@ -29,7 +30,6 @@
import org.springframework.security.authentication.password.CompromisedPasswordChecker;
import org.springframework.security.authentication.password.CompromisedPasswordDecision;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.util.Assert;
import org.springframework.util.StringUtils;
import org.springframework.web.client.RestClient;
@@ -60,7 +60,7 @@ public CompromisedPasswordDecision check(@Nullable String password) {
return new CompromisedPasswordDecision(false);
}
byte[] hash = getSha1Digest().digest(password.getBytes(StandardCharsets.UTF_8));
- String encoded = new String(Hex.encode(hash)).toUpperCase(Locale.ROOT);
+ String encoded = HexFormat.of().formatHex(hash).toUpperCase(Locale.ROOT);
String prefix = encoded.substring(0, PREFIX_LENGTH);
String suffix = encoded.substring(PREFIX_LENGTH);
diff --git a/web/src/main/java/org/springframework/security/web/authentication/password/HaveIBeenPwnedRestApiReactivePasswordChecker.java b/web/src/main/java/org/springframework/security/web/authentication/password/HaveIBeenPwnedRestApiReactivePasswordChecker.java
index d3e7b1d53db..8a0991cd489 100644
--- a/web/src/main/java/org/springframework/security/web/authentication/password/HaveIBeenPwnedRestApiReactivePasswordChecker.java
+++ b/web/src/main/java/org/springframework/security/web/authentication/password/HaveIBeenPwnedRestApiReactivePasswordChecker.java
@@ -19,6 +19,7 @@
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
+import java.util.HexFormat;
import java.util.Locale;
import org.apache.commons.logging.Log;
@@ -30,7 +31,6 @@
import org.springframework.security.authentication.password.CompromisedPasswordDecision;
import org.springframework.security.authentication.password.ReactiveCompromisedPasswordChecker;
-import org.springframework.security.crypto.codec.Hex;
import org.springframework.util.Assert;
import org.springframework.util.StringUtils;
import org.springframework.web.reactive.function.client.WebClient;
@@ -57,7 +57,7 @@ public class HaveIBeenPwnedRestApiReactivePasswordChecker implements ReactiveCom
@Override
public Mono