mirror of
https://github.com/google/nomulus.git
synced 2025-07-21 10:16:07 +02:00
Remove java.util.Date (#2373)
There is one remaining instance in JpaTransactionManagerImpl that cannot be removed because DetachingTypedQuery is implementing TypedQuery, which has a method that expectred java.util.Date.
This commit is contained in:
parent
6d2eb2e140
commit
c68583f666
14 changed files with 108 additions and 147 deletions
|
@ -173,17 +173,24 @@ PRESUBMITS = {
|
|||
):
|
||||
"JavaScript files should not include console logging.",
|
||||
PresubmitCheck(
|
||||
r"org\.testcontainers\.shaded\.",
|
||||
r".*org\.testcontainers\.shaded.*",
|
||||
"java",
|
||||
{"/node_modules/"},
|
||||
):
|
||||
"Do not use shaded dependencies from testcontainers.",
|
||||
PresubmitCheck(
|
||||
r"com\.google\.common\.truth\.Truth8",
|
||||
r".*com\.google\.common\.truth\.Truth8.*",
|
||||
"java",
|
||||
{"/node_modules/"},
|
||||
):
|
||||
"Truth8 is deprecated. Use Truth instead.",
|
||||
PresubmitCheck(
|
||||
r".*java\.util\.Date.*",
|
||||
"java",
|
||||
{"/node_modules/", "JpaTransactionManagerImpl.java"},
|
||||
):
|
||||
"Do not use java.util.Date. Use classes in java.time package instead.",
|
||||
|
||||
}
|
||||
|
||||
# Note that this regex only works for one kind of Flyway file. If we want to
|
||||
|
|
|
@ -45,7 +45,6 @@ import java.io.IOException;
|
|||
import java.math.BigDecimal;
|
||||
import java.time.Duration;
|
||||
import java.util.Collection;
|
||||
import java.util.Date;
|
||||
import java.util.Map;
|
||||
import java.util.ServiceLoader;
|
||||
import org.apache.commons.codec.binary.Base64;
|
||||
|
@ -195,10 +194,7 @@ public class DelegatedCredentials extends GoogleCredentials {
|
|||
GenericData responseData = response.parseAs(GenericData.class);
|
||||
String accessToken = validateString(responseData, "access_token", PARSE_ERROR_PREFIX);
|
||||
int expiresInSeconds = validateInt32(responseData, "expires_in", PARSE_ERROR_PREFIX);
|
||||
long expiresAtMilliseconds = clock.nowUtc().getMillis() + expiresInSeconds * 1000L;
|
||||
@SuppressWarnings("JavaUtilDate")
|
||||
AccessToken token = new AccessToken(accessToken, new Date(expiresAtMilliseconds));
|
||||
return token;
|
||||
return new AccessToken(accessToken, clock.nowUtc().plusSeconds(expiresInSeconds).toDate());
|
||||
}
|
||||
|
||||
String createAssertion(JsonFactory jsonFactory, long currentTime) throws IOException {
|
||||
|
@ -257,8 +253,7 @@ public class DelegatedCredentials extends GoogleCredentials {
|
|||
if (value == null) {
|
||||
throw new IOException(String.format(VALUE_NOT_FOUND_MESSAGE, errorPrefix, key));
|
||||
}
|
||||
if (value instanceof BigDecimal) {
|
||||
BigDecimal bigDecimalValue = (BigDecimal) value;
|
||||
if (value instanceof BigDecimal bigDecimalValue) {
|
||||
return bigDecimalValue.intValueExact();
|
||||
}
|
||||
if (!(value instanceof Integer)) {
|
||||
|
|
|
@ -31,7 +31,6 @@ import java.security.cert.CertificateFactory;
|
|||
import java.security.cert.X509Certificate;
|
||||
import java.security.interfaces.ECPublicKey;
|
||||
import java.security.interfaces.RSAPublicKey;
|
||||
import java.util.Date;
|
||||
import java.util.stream.Collectors;
|
||||
import javax.inject.Inject;
|
||||
import org.bouncycastle.jcajce.provider.asymmetric.util.EC5Util;
|
||||
|
@ -106,12 +105,9 @@ public class CertificateChecker {
|
|||
// These 2 different instances of PublicKey need to be handled separately since their OIDs are
|
||||
// encoded differently. More details on this can be found at
|
||||
// https://stackoverflow.com/questions/49895713/how-to-find-the-matching-curve-name-from-an-ecpublickey.
|
||||
if (key instanceof ECPublicKey) {
|
||||
ECPublicKey ecKey = (ECPublicKey) key;
|
||||
if (key instanceof ECPublicKey ecKey) {
|
||||
params = EC5Util.convertSpec(ecKey.getParams());
|
||||
} else if (key instanceof org.bouncycastle.jce.interfaces.ECPublicKey) {
|
||||
org.bouncycastle.jce.interfaces.ECPublicKey ecKey =
|
||||
(org.bouncycastle.jce.interfaces.ECPublicKey) key;
|
||||
} else if (key instanceof org.bouncycastle.jce.interfaces.ECPublicKey ecKey) {
|
||||
params = ecKey.getParameters();
|
||||
} else {
|
||||
throw new IllegalArgumentException("Unrecognized instance of PublicKey.");
|
||||
|
@ -148,7 +144,7 @@ public class CertificateChecker {
|
|||
if (!violations.isEmpty()) {
|
||||
String displayMessages =
|
||||
violations.stream()
|
||||
.map(violation -> getViolationDisplayMessage(violation))
|
||||
.map(this::getViolationDisplayMessage)
|
||||
.collect(Collectors.joining("\n"));
|
||||
throw new InsecureCertificateException(violations, displayMessages);
|
||||
}
|
||||
|
@ -162,7 +158,7 @@ public class CertificateChecker {
|
|||
ImmutableSet.Builder<CertificateViolation> violations = new ImmutableSet.Builder<>();
|
||||
|
||||
// Check if currently in validity period
|
||||
Date now = clock.nowUtc().toDate();
|
||||
DateTime now = clock.nowUtc();
|
||||
if (DateTimeComparator.getInstance().compare(certificate.getNotAfter(), now) < 0) {
|
||||
violations.add(CertificateViolation.EXPIRED);
|
||||
} else if (DateTimeComparator.getInstance().compare(certificate.getNotBefore(), now) > 0) {
|
||||
|
@ -231,13 +227,13 @@ public class CertificateChecker {
|
|||
DateTime lastExpiringNotificationSentDate, String certificateStr) {
|
||||
X509Certificate certificate = getCertificate(certificateStr);
|
||||
DateTime now = clock.nowUtc();
|
||||
// expiration date is one day after lastValidDate
|
||||
// the expiration date is one day after lastValidDate
|
||||
DateTime lastValidDate = new DateTime(certificate.getNotAfter());
|
||||
if (lastValidDate.isBefore(now)) {
|
||||
return false;
|
||||
}
|
||||
/*
|
||||
* Client should receive a notification if :
|
||||
* Client should receive a notification if:
|
||||
* 1) client has never received notification (lastExpiringNotificationSentDate is initially
|
||||
* set to START_OF_TIME) and the certificate has entered the expiring period, OR
|
||||
* 2) client has received notification but the interval between now and
|
||||
|
@ -254,29 +250,21 @@ public class CertificateChecker {
|
|||
// Yes, we'd rather do this as an instance method on the CertificateViolation enum itself, but
|
||||
// we can't because we need access to configuration (injected as instance variables) which you
|
||||
// can't get in a static enum context.
|
||||
switch (certificateViolation) {
|
||||
case EXPIRED:
|
||||
return "Certificate is expired.";
|
||||
case NOT_YET_VALID:
|
||||
return "Certificate start date is in the future.";
|
||||
case ALGORITHM_CONSTRAINED:
|
||||
return "Certificate key algorithm must be RSA or ECDSA.";
|
||||
case RSA_KEY_LENGTH_TOO_SHORT:
|
||||
return String.format(
|
||||
"RSA key length is too short; the minimum allowed length is %d bits.",
|
||||
this.minimumRsaKeyLength);
|
||||
case VALIDITY_LENGTH_TOO_LONG:
|
||||
return String.format(
|
||||
"Certificate validity period is too long; it must be less than or equal to %d days.",
|
||||
this.maxValidityLengthSchedule.lastEntry().getValue());
|
||||
case INVALID_ECDSA_CURVE:
|
||||
return String.format(
|
||||
"The ECDSA key must use one of these algorithms: %s", allowedEcdsaCurves);
|
||||
default:
|
||||
throw new IllegalArgumentException(
|
||||
String.format(
|
||||
"Unknown CertificateViolation enum value: %s", certificateViolation.name()));
|
||||
}
|
||||
return switch (certificateViolation) {
|
||||
case EXPIRED -> "Certificate is expired.";
|
||||
case NOT_YET_VALID -> "Certificate start date is in the future.";
|
||||
case ALGORITHM_CONSTRAINED -> "Certificate key algorithm must be RSA or ECDSA.";
|
||||
case RSA_KEY_LENGTH_TOO_SHORT ->
|
||||
String.format(
|
||||
"RSA key length is too short; the minimum allowed length is %d bits.",
|
||||
this.minimumRsaKeyLength);
|
||||
case VALIDITY_LENGTH_TOO_LONG ->
|
||||
String.format(
|
||||
"Certificate validity period is too long; it must be less than or equal to %d days.",
|
||||
this.maxValidityLengthSchedule.lastEntry().getValue());
|
||||
case INVALID_ECDSA_CURVE ->
|
||||
String.format("The ECDSA key must use one of these algorithms: %s", allowedEcdsaCurves);
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -295,7 +283,7 @@ public class CertificateChecker {
|
|||
* Gets a suitable end-user-facing display message for this particular certificate violation.
|
||||
*
|
||||
* <p>Note that the {@link CertificateChecker} instance must be passed in because it contains
|
||||
* configuration values (e.g. minimum RSA key length) that go into the error message text.
|
||||
* configuration values (e.g., minimum RSA key length) that go into the error message text.
|
||||
*/
|
||||
public String getDisplayMessage(CertificateChecker certificateChecker) {
|
||||
return certificateChecker.getViolationDisplayMessage(this);
|
||||
|
|
|
@ -127,7 +127,7 @@ public final class TmchCertificateAuthority {
|
|||
*/
|
||||
public void verify(X509Certificate cert) throws GeneralSecurityException {
|
||||
synchronized (TmchCertificateAuthority.class) {
|
||||
X509Utils.verifyCertificate(getAndValidateRoot(), getCrl(), cert, clock.nowUtc().toDate());
|
||||
X509Utils.verifyCertificate(getAndValidateRoot(), getCrl(), cert, clock.nowUtc());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -151,7 +151,7 @@ public final class TmchCertificateAuthority {
|
|||
} catch (Exception e) {
|
||||
logger.atWarning().withCause(e).log("Old CRL is invalid, ignored during CRL update.");
|
||||
}
|
||||
X509Utils.verifyCrl(getAndValidateRoot(), oldCrl, newCrl, clock.nowUtc().toDate());
|
||||
X509Utils.verifyCrl(getAndValidateRoot(), oldCrl, newCrl, clock.nowUtc());
|
||||
TmchCrl.set(asciiCrl, url);
|
||||
}
|
||||
|
||||
|
|
|
@ -22,7 +22,7 @@ import google.registry.model.domain.token.AllocationToken;
|
|||
import google.registry.model.domain.token.AllocationToken.TokenType;
|
||||
import google.registry.model.domain.token.BulkPricingPackage;
|
||||
import google.registry.persistence.VKey;
|
||||
import java.util.Date;
|
||||
import google.registry.tools.params.DateTimeParameter;
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import javax.annotation.Nullable;
|
||||
|
@ -56,9 +56,11 @@ abstract class CreateOrUpdateBulkPricingPackageCommand extends MutatingCommand {
|
|||
@Nullable
|
||||
@Parameter(
|
||||
names = "--next_billing_date",
|
||||
converter = DateTimeParameter.class,
|
||||
validateWith = DateTimeParameter.class,
|
||||
description =
|
||||
"The next date that the bulk pricing package should be billed for its annual fee")
|
||||
Date nextBillingDate;
|
||||
DateTime nextBillingDate;
|
||||
|
||||
/** Returns the existing BulkPricingPackage or null if it does not exist. */
|
||||
@Nullable
|
||||
|
@ -105,9 +107,7 @@ abstract class CreateOrUpdateBulkPricingPackageCommand extends MutatingCommand {
|
|||
Optional.ofNullable(maxCreates).ifPresent(builder::setMaxCreates);
|
||||
Optional.ofNullable(price).ifPresent(builder::setBulkPrice);
|
||||
Optional.ofNullable(nextBillingDate)
|
||||
.ifPresent(
|
||||
nextBillingDate ->
|
||||
builder.setNextBillingDate(new DateTime(nextBillingDate)));
|
||||
.ifPresent(nextBillingDate -> builder.setNextBillingDate(nextBillingDate));
|
||||
if (clearLastNotificationSent()) {
|
||||
builder.setLastNotificationSent(null);
|
||||
}
|
||||
|
|
|
@ -18,6 +18,7 @@ import static com.google.common.truth.Truth.assertThat;
|
|||
|
||||
import com.google.common.base.Splitter;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import com.google.common.collect.ImmutableMap;
|
||||
import google.registry.module.backend.BackendRequestComponent;
|
||||
import google.registry.module.bsa.BsaRequestComponent;
|
||||
import google.registry.module.frontend.FrontendRequestComponent;
|
||||
|
@ -28,7 +29,6 @@ import google.registry.testing.TestDataHelper;
|
|||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.testcontainers.shaded.com.google.common.collect.ImmutableMap;
|
||||
|
||||
/** Unit tests for {@link RequestComponent}. */
|
||||
public class RequestComponentTest {
|
||||
|
|
|
@ -40,7 +40,6 @@ import com.google.common.collect.Multimap;
|
|||
import com.google.common.collect.Multimaps;
|
||||
import com.google.common.net.HttpHeaders;
|
||||
import com.google.common.net.MediaType;
|
||||
import com.google.common.truth.Truth8;
|
||||
import com.google.protobuf.Timestamp;
|
||||
import com.google.protobuf.util.Timestamps;
|
||||
import dagger.Module;
|
||||
|
@ -133,7 +132,7 @@ public class CloudTasksHelper implements Serializable {
|
|||
public void assertTasksEnqueuedWithProperty(
|
||||
String queueName, Function<Task, String> propertyGetter, String... expectedTaskProperties) {
|
||||
// Ordering is irrelevant but duplicates should be considered independently.
|
||||
Truth8.assertThat(getTestTasksFor(queueName).stream().map(propertyGetter))
|
||||
assertThat(getTestTasksFor(queueName).stream().map(propertyGetter))
|
||||
.containsExactly((Object[]) expectedTaskProperties);
|
||||
}
|
||||
|
||||
|
|
|
@ -53,7 +53,7 @@ public class CreateBulkPricingPackageCommandTest
|
|||
"--max_domains=100",
|
||||
"--max_creates=500",
|
||||
"--price=USD 1000.00",
|
||||
"--next_billing_date=2012-03-17",
|
||||
"--next_billing_date=2012-03-17T00:00:00Z",
|
||||
"abc123");
|
||||
|
||||
Optional<BulkPricingPackage> bulkPricingPackageOptional =
|
||||
|
@ -161,7 +161,7 @@ public class CreateBulkPricingPackageCommandTest
|
|||
.setAllowedEppActions(ImmutableSet.of(CommandName.CREATE))
|
||||
.setDiscountFraction(1)
|
||||
.build());
|
||||
runCommandForced("--price=USD 1000.00", "--next_billing_date=2012-03-17", "abc123");
|
||||
runCommandForced("--price=USD 1000.00", "--next_billing_date=2012-03-17T00:00:00Z", "abc123");
|
||||
Optional<BulkPricingPackage> bulkPricingPackageOptional =
|
||||
tm().transact(() -> BulkPricingPackage.loadByTokenString("abc123"));
|
||||
assertThat(bulkPricingPackageOptional).isPresent();
|
||||
|
|
|
@ -69,7 +69,7 @@ public class UpdateBulkPricingPackageCommandTest
|
|||
"--max_domains=200",
|
||||
"--max_creates=1000",
|
||||
"--price=USD 2000.00",
|
||||
"--next_billing_date=2013-03-17",
|
||||
"--next_billing_date=2013-03-17T00:00:00Z",
|
||||
"--clear_last_notification_sent",
|
||||
"abc123");
|
||||
|
||||
|
@ -106,7 +106,7 @@ public class UpdateBulkPricingPackageCommandTest
|
|||
"--max_domains=100",
|
||||
"--max_creates=500",
|
||||
"--price=USD 1000.00",
|
||||
"--next_billing_date=2012-03-17",
|
||||
"--next_billing_date=2012-03-17T00:00:00Z",
|
||||
"nullPackage"));
|
||||
Truth.assertThat(thrown.getMessage())
|
||||
.isEqualTo("BulkPricingPackage with token nullPackage does not exist");
|
||||
|
@ -117,7 +117,7 @@ public class UpdateBulkPricingPackageCommandTest
|
|||
runCommandForced(
|
||||
"--max_creates=1000",
|
||||
"--price=USD 2000.00",
|
||||
"--next_billing_date=2013-03-17",
|
||||
"--next_billing_date=2013-03-17T00:00:00Z",
|
||||
"--clear_last_notification_sent",
|
||||
"abc123");
|
||||
|
||||
|
@ -159,7 +159,7 @@ public class UpdateBulkPricingPackageCommandTest
|
|||
runCommandForced(
|
||||
"--max_domains=200",
|
||||
"--max_creates=1000",
|
||||
"--next_billing_date=2013-03-17",
|
||||
"--next_billing_date=2013-03-17T00:00:00Z",
|
||||
"--clear_last_notification_sent",
|
||||
"abc123");
|
||||
|
||||
|
|
|
@ -19,6 +19,7 @@ import static google.registry.networking.handler.SslInitializerTestUtils.getKeyP
|
|||
import static google.registry.networking.handler.SslInitializerTestUtils.setUpSslChannel;
|
||||
import static google.registry.networking.handler.SslInitializerTestUtils.signKeyPair;
|
||||
import static google.registry.networking.handler.SslInitializerTestUtils.verifySslException;
|
||||
import static org.joda.time.DateTimeZone.UTC;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import google.registry.util.SelfSignedCaCertificate;
|
||||
|
@ -43,12 +44,10 @@ import java.security.cert.CertificateException;
|
|||
import java.security.cert.CertificateExpiredException;
|
||||
import java.security.cert.CertificateNotYetValidException;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.time.Duration;
|
||||
import java.time.Instant;
|
||||
import java.util.Date;
|
||||
import java.util.stream.Stream;
|
||||
import javax.net.ssl.SSLException;
|
||||
import javax.net.ssl.SSLSession;
|
||||
import org.joda.time.DateTime;
|
||||
import org.junit.jupiter.api.extension.RegisterExtension;
|
||||
import org.junit.jupiter.params.ParameterizedTest;
|
||||
import org.junit.jupiter.params.provider.Arguments;
|
||||
|
@ -62,7 +61,7 @@ import org.junit.jupiter.params.provider.MethodSource;
|
|||
* the overhead of routing traffic through the network layer, even if it were to go through
|
||||
* loopback. It also alleviates the need to pick a free port to use.
|
||||
*
|
||||
* <p>The local addresses used in each test method must to be different, otherwise tests run in
|
||||
* <p>The local addresses used in each test method must be different, otherwise tests run in
|
||||
* parallel may interfere with each other.
|
||||
*/
|
||||
class SslClientInitializerTest {
|
||||
|
@ -204,7 +203,7 @@ class SslClientInitializerTest {
|
|||
// Generate a new key pair.
|
||||
KeyPair keyPair = getKeyPair();
|
||||
|
||||
// Generate a self signed certificate, and use it to sign the key pair.
|
||||
// Generate a self-signed certificate, and use it to sign the key pair.
|
||||
SelfSignedCaCertificate ssc = SelfSignedCaCertificate.create();
|
||||
X509Certificate cert = signKeyPair(ssc, keyPair, SSL_HOST);
|
||||
|
||||
|
@ -212,7 +211,7 @@ class SslClientInitializerTest {
|
|||
PrivateKey privateKey = keyPair.getPrivate();
|
||||
nettyExtension.setUpServer(localAddress, getServerHandler(false, privateKey, cert));
|
||||
|
||||
// Set up the client to trust the self signed cert used to sign the cert that server provides.
|
||||
// Set up the client to trust the self-signed cert used to sign the cert that server provides.
|
||||
SslClientInitializer<LocalChannel> sslClientInitializer =
|
||||
new SslClientInitializer<>(
|
||||
sslProvider,
|
||||
|
@ -239,21 +238,17 @@ class SslClientInitializerTest {
|
|||
// Generate a new key pair.
|
||||
KeyPair keyPair = getKeyPair();
|
||||
|
||||
// Generate a self signed certificate, and use it to sign the key pair.
|
||||
// Generate a self-signed certificate, and use it to sign the key pair.
|
||||
SelfSignedCaCertificate ssc = SelfSignedCaCertificate.create();
|
||||
X509Certificate cert =
|
||||
signKeyPair(
|
||||
ssc,
|
||||
keyPair,
|
||||
SSL_HOST,
|
||||
Date.from(Instant.now().minus(Duration.ofDays(2))),
|
||||
Date.from(Instant.now().minus(Duration.ofDays(1))));
|
||||
ssc, keyPair, SSL_HOST, DateTime.now(UTC).minusDays(2), DateTime.now(UTC).minusDays(1));
|
||||
|
||||
// Set up the server to use the signed cert and private key to perform handshake;
|
||||
PrivateKey privateKey = keyPair.getPrivate();
|
||||
nettyExtension.setUpServer(localAddress, getServerHandler(false, privateKey, cert));
|
||||
|
||||
// Set up the client to trust the self signed cert used to sign the cert that server provides.
|
||||
// Set up the client to trust the self-signed cert used to sign the cert that server provides.
|
||||
SslClientInitializer<LocalChannel> sslClientInitializer =
|
||||
new SslClientInitializer<>(
|
||||
sslProvider,
|
||||
|
@ -280,21 +275,17 @@ class SslClientInitializerTest {
|
|||
// Generate a new key pair.
|
||||
KeyPair keyPair = getKeyPair();
|
||||
|
||||
// Generate a self signed certificate, and use it to sign the key pair.
|
||||
// Generate a self-signed certificate, and use it to sign the key pair.
|
||||
SelfSignedCaCertificate ssc = SelfSignedCaCertificate.create();
|
||||
X509Certificate cert =
|
||||
signKeyPair(
|
||||
ssc,
|
||||
keyPair,
|
||||
SSL_HOST,
|
||||
Date.from(Instant.now().plus(Duration.ofDays(1))),
|
||||
Date.from(Instant.now().plus(Duration.ofDays(2))));
|
||||
ssc, keyPair, SSL_HOST, DateTime.now(UTC).plusDays(1), DateTime.now(UTC).plusDays(2));
|
||||
|
||||
// Set up the server to use the signed cert and private key to perform handshake;
|
||||
PrivateKey privateKey = keyPair.getPrivate();
|
||||
nettyExtension.setUpServer(localAddress, getServerHandler(false, privateKey, cert));
|
||||
|
||||
// Set up the client to trust the self signed cert used to sign the cert that server provides.
|
||||
// Set up the client to trust the self-signed cert used to sign the cert that server provides.
|
||||
SslClientInitializer<LocalChannel> sslClientInitializer =
|
||||
new SslClientInitializer<>(
|
||||
sslProvider,
|
||||
|
@ -333,7 +324,7 @@ class SslClientInitializerTest {
|
|||
SslClientInitializerTest::hostProvider,
|
||||
SslClientInitializerTest::portProvider,
|
||||
ImmutableList.of(serverSsc.cert()),
|
||||
() -> clientSsc.key(),
|
||||
clientSsc::key,
|
||||
() -> ImmutableList.of(clientSsc.cert()));
|
||||
nettyExtension.setUpClient(localAddress, sslClientInitializer);
|
||||
|
||||
|
@ -360,7 +351,7 @@ class SslClientInitializerTest {
|
|||
// Generate a new key pair.
|
||||
KeyPair keyPair = getKeyPair();
|
||||
|
||||
// Generate a self signed certificate, and use it to sign the key pair.
|
||||
// Generate a self-signed certificate, and use it to sign the key pair.
|
||||
SelfSignedCaCertificate ssc = SelfSignedCaCertificate.create();
|
||||
X509Certificate cert = signKeyPair(ssc, keyPair, "wrong.com");
|
||||
|
||||
|
@ -368,7 +359,7 @@ class SslClientInitializerTest {
|
|||
PrivateKey privateKey = keyPair.getPrivate();
|
||||
nettyExtension.setUpServer(localAddress, getServerHandler(false, privateKey, cert));
|
||||
|
||||
// Set up the client to trust the self signed cert used to sign the cert that server provides.
|
||||
// Set up the client to trust the self-signed cert used to sign the cert that server provides.
|
||||
SslClientInitializer<LocalChannel> sslClientInitializer =
|
||||
new SslClientInitializer<>(
|
||||
sslProvider,
|
||||
|
@ -379,7 +370,7 @@ class SslClientInitializerTest {
|
|||
null);
|
||||
nettyExtension.setUpClient(localAddress, sslClientInitializer);
|
||||
|
||||
// When the client rejects the server cert due to wrong hostname, both the client and server
|
||||
// When the client rejects the server cert due to the wrong hostname, both the client and server
|
||||
// should throw exceptions.
|
||||
nettyExtension.assertThatClientRootCause().isInstanceOf(CertificateException.class);
|
||||
nettyExtension.assertThatClientRootCause().hasMessageThat().contains(SSL_HOST);
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
package google.registry.networking.handler;
|
||||
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
import static org.joda.time.DateTimeZone.UTC;
|
||||
import static org.junit.jupiter.api.Assertions.assertThrows;
|
||||
|
||||
import com.google.common.base.Throwables;
|
||||
|
@ -27,9 +28,6 @@ import java.security.KeyPair;
|
|||
import java.security.KeyPairGenerator;
|
||||
import java.security.SecureRandom;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.time.Duration;
|
||||
import java.time.Instant;
|
||||
import java.util.Date;
|
||||
import java.util.concurrent.ExecutionException;
|
||||
import javax.net.ssl.SSLSession;
|
||||
import org.bouncycastle.asn1.x500.X500Name;
|
||||
|
@ -40,6 +38,7 @@ import org.bouncycastle.cert.jcajce.JcaX509v3CertificateBuilder;
|
|||
import org.bouncycastle.jce.provider.BouncyCastleProvider;
|
||||
import org.bouncycastle.operator.ContentSigner;
|
||||
import org.bouncycastle.operator.jcajce.JcaContentSignerBuilder;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
/**
|
||||
* Utility class that provides methods used by {@link SslClientInitializerTest} and {@link
|
||||
|
@ -67,13 +66,13 @@ public final class SslInitializerTestUtils {
|
|||
}
|
||||
|
||||
/**
|
||||
* Signs the given key pair with the given self signed certificate to generate a certificate with
|
||||
* Signs the given key pair with the given self-signed certificate to generate a certificate with
|
||||
* the given validity range.
|
||||
*
|
||||
* @return signed public key (of the key pair) certificate
|
||||
*/
|
||||
public static X509Certificate signKeyPair(
|
||||
SelfSignedCaCertificate ssc, KeyPair keyPair, String hostname, Date from, Date to)
|
||||
SelfSignedCaCertificate ssc, KeyPair keyPair, String hostname, DateTime from, DateTime to)
|
||||
throws Exception {
|
||||
X500Name subjectDnName = new X500Name("CN=" + hostname);
|
||||
BigInteger serialNumber = BigInteger.valueOf(System.currentTimeMillis());
|
||||
|
@ -81,7 +80,12 @@ public final class SslInitializerTestUtils {
|
|||
ContentSigner sigGen = new JcaContentSignerBuilder("SHA256WithRSAEncryption").build(ssc.key());
|
||||
X509v3CertificateBuilder v3CertGen =
|
||||
new JcaX509v3CertificateBuilder(
|
||||
issuerDnName, serialNumber, from, to, subjectDnName, keyPair.getPublic());
|
||||
issuerDnName,
|
||||
serialNumber,
|
||||
from.toDate(),
|
||||
to.toDate(),
|
||||
subjectDnName,
|
||||
keyPair.getPublic());
|
||||
|
||||
X509CertificateHolder certificateHolder = v3CertGen.build(sigGen);
|
||||
return new JcaX509CertificateConverter()
|
||||
|
@ -90,7 +94,7 @@ public final class SslInitializerTestUtils {
|
|||
}
|
||||
|
||||
/**
|
||||
* Signs the given key pair with the given self signed certificate to generate a certificate that
|
||||
* Signs the given key pair with the given self-signed certificate to generate a certificate that
|
||||
* is valid from yesterday to tomorrow.
|
||||
*
|
||||
* @return signed public key (of the key pair) certificate
|
||||
|
@ -98,11 +102,7 @@ public final class SslInitializerTestUtils {
|
|||
public static X509Certificate signKeyPair(
|
||||
SelfSignedCaCertificate ssc, KeyPair keyPair, String hostname) throws Exception {
|
||||
return signKeyPair(
|
||||
ssc,
|
||||
keyPair,
|
||||
hostname,
|
||||
Date.from(Instant.now().minus(Duration.ofDays(1))),
|
||||
Date.from(Instant.now().plus(Duration.ofDays(1))));
|
||||
ssc, keyPair, hostname, DateTime.now(UTC).minusDays(1), DateTime.now(UTC).plusDays(1));
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -110,7 +110,7 @@ public final class SslInitializerTestUtils {
|
|||
* and verifies if it is echoed back correctly.
|
||||
*
|
||||
* @param certs The certificate that the server should provide.
|
||||
* @return The SSL session in current channel, can be used for further validation.
|
||||
* @return The SSL session in the current channel, can be used for further validation.
|
||||
*/
|
||||
static SSLSession setUpSslChannel(Channel channel, X509Certificate... certs) throws Exception {
|
||||
SslHandler sslHandler = channel.pipeline().get(SslHandler.class);
|
||||
|
|
|
@ -20,6 +20,7 @@ import static google.registry.networking.handler.SslInitializerTestUtils.setUpSs
|
|||
import static google.registry.networking.handler.SslInitializerTestUtils.signKeyPair;
|
||||
import static google.registry.networking.handler.SslInitializerTestUtils.verifySslException;
|
||||
import static google.registry.networking.handler.SslServerInitializer.CLIENT_CERTIFICATE_PROMISE_KEY;
|
||||
import static org.joda.time.DateTimeZone.UTC;
|
||||
|
||||
import com.google.common.base.Suppliers;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
|
@ -41,11 +42,8 @@ import java.security.cert.CertificateException;
|
|||
import java.security.cert.CertificateExpiredException;
|
||||
import java.security.cert.CertificateNotYetValidException;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.time.Duration;
|
||||
import java.time.Instant;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
import java.util.stream.Stream;
|
||||
import javax.net.ssl.SSLEngine;
|
||||
|
@ -53,6 +51,7 @@ import javax.net.ssl.SSLException;
|
|||
import javax.net.ssl.SSLHandshakeException;
|
||||
import javax.net.ssl.SSLParameters;
|
||||
import javax.net.ssl.SSLSession;
|
||||
import org.joda.time.DateTime;
|
||||
import org.junit.jupiter.api.extension.RegisterExtension;
|
||||
import org.junit.jupiter.params.ParameterizedTest;
|
||||
import org.junit.jupiter.params.provider.Arguments;
|
||||
|
@ -66,7 +65,7 @@ import org.junit.jupiter.params.provider.MethodSource;
|
|||
* the overhead of routing traffic through the network layer, even if it were to go through
|
||||
* loopback. It also alleviates the need to pick a free port to use.
|
||||
*
|
||||
* <p>The local addresses used in each test method must to be different, otherwise tests run in
|
||||
* <p>The local addresses used in each test method must be different, otherwise tests run in
|
||||
* parallel may interfere with each other.
|
||||
*/
|
||||
class SslServerInitializerTest {
|
||||
|
@ -202,9 +201,7 @@ class SslServerInitializerTest {
|
|||
localAddress, getServerHandler(true, true, sslProvider, serverSsc.key(), serverSsc.cert()));
|
||||
SelfSignedCaCertificate clientSsc =
|
||||
SelfSignedCaCertificate.create(
|
||||
"CLIENT",
|
||||
Date.from(Instant.now().minus(Duration.ofDays(2))),
|
||||
Date.from(Instant.now().plus(Duration.ofDays(1))));
|
||||
"CLIENT", DateTime.now(UTC).minusDays(2), DateTime.now(UTC).plusDays(1));
|
||||
nettyExtension.setUpClient(
|
||||
localAddress,
|
||||
getClientHandler(
|
||||
|
@ -237,9 +234,7 @@ class SslServerInitializerTest {
|
|||
Suppliers.ofInstance(ImmutableList.of(serverSsc.cert()))));
|
||||
SelfSignedCaCertificate clientSsc =
|
||||
SelfSignedCaCertificate.create(
|
||||
"CLIENT",
|
||||
Date.from(Instant.now().minus(Duration.ofDays(2))),
|
||||
Date.from(Instant.now().plus(Duration.ofDays(1))));
|
||||
"CLIENT", DateTime.now(UTC).minusDays(2), DateTime.now(UTC).plusDays(1));
|
||||
nettyExtension.setUpClient(
|
||||
localAddress,
|
||||
getClientHandler(
|
||||
|
@ -271,20 +266,18 @@ class SslServerInitializerTest {
|
|||
localAddress, getServerHandler(true, true, sslProvider, serverSsc.key(), serverSsc.cert()));
|
||||
SelfSignedCaCertificate clientSsc =
|
||||
SelfSignedCaCertificate.create(
|
||||
"CLIENT",
|
||||
Date.from(Instant.now().minus(Duration.ofDays(2))),
|
||||
Date.from(Instant.now().plus(Duration.ofDays(1))));
|
||||
"CLIENT", DateTime.now(UTC).minusDays(2), DateTime.now(UTC).plusDays(1));
|
||||
nettyExtension.setUpClient(
|
||||
localAddress,
|
||||
getClientHandler(
|
||||
sslProvider, serverSsc.cert(), clientSsc.key(), clientSsc.cert(), "TLSv1.1", null));
|
||||
|
||||
ImmutableList<Integer> jdkVersion =
|
||||
Arrays.asList(System.getProperty("java.version").split("\\.")).stream()
|
||||
Arrays.stream(System.getProperty("java.version").split("\\."))
|
||||
.map(Integer::parseInt)
|
||||
.collect(ImmutableList.toImmutableList());
|
||||
|
||||
// In JDK v11.0.11 and above TLS 1.1 is not supported any more, in which case attempting to
|
||||
// In JDK v11.0.11 and above, TLS 1.1 is not supported anymore, in which case attempting to
|
||||
// connect with TLS 1.1 results in a ClosedChannelException instead of a SSLHandShakeException.
|
||||
// See https://www.oracle.com/java/technologies/javase/11-0-11-relnotes.html#JDK-8202343
|
||||
Class<? extends Exception> rootCause =
|
||||
|
@ -309,9 +302,7 @@ class SslServerInitializerTest {
|
|||
localAddress, getServerHandler(true, true, sslProvider, serverSsc.key(), serverSsc.cert()));
|
||||
SelfSignedCaCertificate clientSsc =
|
||||
SelfSignedCaCertificate.create(
|
||||
"CLIENT",
|
||||
Date.from(Instant.now().minus(Duration.ofDays(2))),
|
||||
Date.from(Instant.now().minus(Duration.ofDays(1))));
|
||||
"CLIENT", DateTime.now(UTC).minusDays(2), DateTime.now(UTC).minusDays(1));
|
||||
nettyExtension.setUpClient(
|
||||
localAddress,
|
||||
getClientHandler(sslProvider, serverSsc.cert(), clientSsc.key(), clientSsc.cert()));
|
||||
|
@ -332,9 +323,7 @@ class SslServerInitializerTest {
|
|||
localAddress, getServerHandler(true, true, sslProvider, serverSsc.key(), serverSsc.cert()));
|
||||
SelfSignedCaCertificate clientSsc =
|
||||
SelfSignedCaCertificate.create(
|
||||
"CLIENT",
|
||||
Date.from(Instant.now().plus(Duration.ofDays(1))),
|
||||
Date.from(Instant.now().plus(Duration.ofDays(2))));
|
||||
"CLIENT", DateTime.now(UTC).plusDays(1), DateTime.now(UTC).plusDays(2));
|
||||
nettyExtension.setUpClient(
|
||||
localAddress,
|
||||
getClientHandler(sslProvider, serverSsc.cert(), clientSsc.key(), clientSsc.cert()));
|
||||
|
@ -446,8 +435,8 @@ class SslServerInitializerTest {
|
|||
localAddress,
|
||||
getClientHandler(sslProvider, serverSsc.cert(), clientSsc.key(), clientSsc.cert()));
|
||||
|
||||
// When the client rejects the server cert due to wrong hostname, both the server and the client
|
||||
// throw exceptions.
|
||||
// When the client rejects the server cert due to the wrong hostname, both the server and the
|
||||
// client throw exceptions.
|
||||
nettyExtension.assertThatClientRootCause().isInstanceOf(CertificateException.class);
|
||||
nettyExtension.assertThatClientRootCause().hasMessageThat().contains(SSL_HOST);
|
||||
nettyExtension.assertThatServerRootCause().isInstanceOf(SSLException.class);
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
package google.registry.util;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkArgument;
|
||||
import static org.joda.time.DateTimeZone.UTC;
|
||||
|
||||
import com.google.common.collect.ImmutableMap;
|
||||
import java.math.BigInteger;
|
||||
|
@ -23,9 +24,6 @@ import java.security.KeyPairGenerator;
|
|||
import java.security.PrivateKey;
|
||||
import java.security.SecureRandom;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.time.Duration;
|
||||
import java.time.Instant;
|
||||
import java.util.Date;
|
||||
import java.util.Random;
|
||||
import org.bouncycastle.asn1.ASN1ObjectIdentifier;
|
||||
import org.bouncycastle.asn1.x500.X500Name;
|
||||
|
@ -44,9 +42,8 @@ import org.joda.time.DateTime;
|
|||
public class SelfSignedCaCertificate {
|
||||
|
||||
private static final String DEFAULT_ISSUER_FQDN = "registry-test";
|
||||
private static final Date DEFAULT_NOT_BEFORE =
|
||||
Date.from(Instant.now().minus(Duration.ofHours(1)));
|
||||
private static final Date DEFAULT_NOT_AFTER = Date.from(Instant.now().plus(Duration.ofDays(1)));
|
||||
private static final DateTime DEFAULT_NOT_BEFORE = DateTime.now(UTC).minusHours(1);
|
||||
private static final DateTime DEFAULT_NOT_AFTER = DateTime.now(UTC).plusDays(1);
|
||||
|
||||
private static final Random RANDOM = new Random();
|
||||
private static final BouncyCastleProvider PROVIDER = new BouncyCastleProvider();
|
||||
|
@ -80,24 +77,14 @@ public class SelfSignedCaCertificate {
|
|||
return create(fqdn, DEFAULT_NOT_BEFORE, DEFAULT_NOT_AFTER);
|
||||
}
|
||||
|
||||
public static SelfSignedCaCertificate create(String fqdn, Date from, Date to) throws Exception {
|
||||
return create(keyGen.generateKeyPair(), fqdn, from, to);
|
||||
}
|
||||
|
||||
public static SelfSignedCaCertificate create(String fqdn, DateTime from, DateTime to)
|
||||
throws Exception {
|
||||
return create(keyGen.generateKeyPair(), fqdn, from.toDate(), to.toDate());
|
||||
}
|
||||
|
||||
public static SelfSignedCaCertificate create(KeyPair keyPair, String fqdn, Date from, Date to)
|
||||
throws Exception {
|
||||
return new SelfSignedCaCertificate(keyPair.getPrivate(), createCaCert(keyPair, fqdn, from, to));
|
||||
return create(keyGen.generateKeyPair(), fqdn, from, to);
|
||||
}
|
||||
|
||||
public static SelfSignedCaCertificate create(
|
||||
KeyPair keyPair, String fqdn, DateTime from, DateTime to) throws Exception {
|
||||
return new SelfSignedCaCertificate(
|
||||
keyPair.getPrivate(), createCaCert(keyPair, fqdn, from.toDate(), to.toDate()));
|
||||
return new SelfSignedCaCertificate(keyPair.getPrivate(), createCaCert(keyPair, fqdn, from, to));
|
||||
}
|
||||
|
||||
static KeyPairGenerator createKeyPairGenerator() {
|
||||
|
@ -111,7 +98,7 @@ public class SelfSignedCaCertificate {
|
|||
}
|
||||
|
||||
/** Returns a self-signed Certificate Authority (CA) certificate. */
|
||||
static X509Certificate createCaCert(KeyPair keyPair, String fqdn, Date from, Date to)
|
||||
static X509Certificate createCaCert(KeyPair keyPair, String fqdn, DateTime from, DateTime to)
|
||||
throws Exception {
|
||||
X500Name owner = new X500Name("CN=" + fqdn);
|
||||
String publicKeyAlg = keyPair.getPublic().getAlgorithm();
|
||||
|
@ -121,7 +108,12 @@ public class SelfSignedCaCertificate {
|
|||
new JcaContentSignerBuilder(signatureAlgorithm).build(keyPair.getPrivate());
|
||||
X509v3CertificateBuilder builder =
|
||||
new JcaX509v3CertificateBuilder(
|
||||
owner, new BigInteger(64, RANDOM), from, to, owner, keyPair.getPublic());
|
||||
owner,
|
||||
new BigInteger(64, RANDOM),
|
||||
from.toDate(),
|
||||
to.toDate(),
|
||||
owner,
|
||||
keyPair.getPublic());
|
||||
|
||||
// Mark cert as CA by adding basicConstraint with cA=true to the builder
|
||||
BasicConstraints basicConstraints = new BasicConstraints(true);
|
||||
|
|
|
@ -41,11 +41,11 @@ import java.security.cert.X509CRL;
|
|||
import java.security.cert.X509CRLEntry;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.util.Base64;
|
||||
import java.util.Date;
|
||||
import java.util.NoSuchElementException;
|
||||
import java.util.Optional;
|
||||
import javax.annotation.Nullable;
|
||||
import javax.annotation.Tainted;
|
||||
import org.joda.time.DateTime;
|
||||
import org.joda.time.DateTimeComparator;
|
||||
|
||||
/** X.509 Public Key Infrastructure (PKI) helper functions. */
|
||||
|
@ -140,13 +140,13 @@ public final class X509Utils {
|
|||
* <p>Support for certificate chains has not been implemented.
|
||||
*
|
||||
* @throws GeneralSecurityException for unsupported protocols, certs not signed by the TMCH,
|
||||
* parsing errors, encoding errors, if the CRL is expired, or if the CRL is older than the
|
||||
* one currently in memory.
|
||||
* parsing errors, encoding errors, if the CRL is expired, or if the CRL is older than the one
|
||||
* currently in memory.
|
||||
*/
|
||||
public static void verifyCertificate(
|
||||
X509Certificate rootCert, X509CRL crl, @Tainted X509Certificate cert, Date now)
|
||||
throws GeneralSecurityException {
|
||||
cert.checkValidity(checkNotNull(now, "now"));
|
||||
X509Certificate rootCert, X509CRL crl, @Tainted X509Certificate cert, DateTime now)
|
||||
throws GeneralSecurityException {
|
||||
cert.checkValidity(checkNotNull(now, "now").toDate());
|
||||
cert.verify(rootCert.getPublicKey());
|
||||
if (crl.isRevoked(cert)) {
|
||||
X509CRLEntry entry = crl.getRevokedCertificate(cert);
|
||||
|
@ -168,7 +168,7 @@ public final class X509Utils {
|
|||
* incorrect keys, and for invalid, old, not-yet-valid or revoked certificates.
|
||||
*/
|
||||
public static void verifyCrl(
|
||||
X509Certificate rootCert, @Nullable X509CRL oldCrl, @Tainted X509CRL newCrl, Date now)
|
||||
X509Certificate rootCert, @Nullable X509CRL oldCrl, @Tainted X509CRL newCrl, DateTime now)
|
||||
throws GeneralSecurityException {
|
||||
if (oldCrl != null
|
||||
&& DateTimeComparator.getInstance().compare(newCrl.getThisUpdate(), oldCrl.getThisUpdate())
|
||||
|
@ -178,7 +178,7 @@ public final class X509Utils {
|
|||
"New CRL is more out of date than our current CRL. %s < %s\n%s",
|
||||
newCrl.getThisUpdate(), oldCrl.getThisUpdate(), newCrl));
|
||||
}
|
||||
if (DateTimeComparator.getInstance().compare(newCrl.getNextUpdate(), now) < 0) {
|
||||
if (DateTimeComparator.getInstance().compare(new DateTime(newCrl.getNextUpdate()), now) < 0) {
|
||||
throw new CRLException("CRL has expired.\n" + newCrl);
|
||||
}
|
||||
newCrl.verify(rootCert.getPublicKey());
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue