Add ReservedList to CloudSQL in unit tests (#992)

* Add ReservedList to CloudSQL in unit tests

* Remove unnecessary changes

* Change databasehelper to use DualDatabaseDao
This commit is contained in:
sarahcaseybot 2021-03-10 14:16:39 -05:00 committed by GitHub
parent e5801e1b60
commit 79b4cb0d82
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 81 additions and 39 deletions

View file

@ -248,7 +248,7 @@ public final class ReservedList
@Override @Override
public ReservedList load(String listName) { public ReservedList load(String listName) {
return tm().isOfy() return tm().isOfy()
? ReservedListDualWriteDao.getLatestRevision(listName).orElse(null) ? ReservedListDualDatabaseDao.getLatestRevision(listName).orElse(null)
: ReservedListSqlDao.getLatestRevision(listName).orElse(null); : ReservedListSqlDao.getLatestRevision(listName).orElse(null);
} }
}); });

View file

@ -23,6 +23,7 @@ import com.google.common.collect.MapDifference.ValueDifference;
import com.google.common.collect.Maps; import com.google.common.collect.Maps;
import com.google.common.flogger.FluentLogger; import com.google.common.flogger.FluentLogger;
import com.googlecode.objectify.Key; import com.googlecode.objectify.Key;
import google.registry.model.DatabaseMigrationUtils;
import google.registry.model.registry.label.ReservedList.ReservedListEntry; import google.registry.model.registry.label.ReservedList.ReservedListEntry;
import google.registry.persistence.VKey; import google.registry.persistence.VKey;
import java.util.Map; import java.util.Map;
@ -35,24 +36,22 @@ import java.util.Optional;
* <p>TODO(b/160993806): Delete this DAO and switch to use the SQL only DAO after migrating to Cloud * <p>TODO(b/160993806): Delete this DAO and switch to use the SQL only DAO after migrating to Cloud
* SQL. * SQL.
*/ */
public class ReservedListDualWriteDao { public class ReservedListDualDatabaseDao {
private static final FluentLogger logger = FluentLogger.forEnclosingClass(); private static final FluentLogger logger = FluentLogger.forEnclosingClass();
private ReservedListDualWriteDao() {} private ReservedListDualDatabaseDao() {}
/** Persist a new reserved list to Cloud SQL. */ /** Persist a new reserved list to Cloud SQL. */
public static void save(ReservedList reservedList) { public static void save(ReservedList reservedList) {
ofyTm().transact(() -> ofyTm().put(reservedList)); ofyTm().transact(() -> ofyTm().put(reservedList));
try {
logger.atInfo().log("Saving reserved list %s to Cloud SQL", reservedList.getName()); logger.atInfo().log("Saving reserved list %s to Cloud SQL", reservedList.getName());
ReservedListSqlDao.save(reservedList); DatabaseMigrationUtils.suppressExceptionUnlessInTest(
() -> ReservedListSqlDao.save(reservedList),
"Error saving the reserved list to Cloud SQL.");
logger.atInfo().log( logger.atInfo().log(
"Saved reserved list %s with %d entries to Cloud SQL", "Saved reserved list %s with %d entries to Cloud SQL",
reservedList.getName(), reservedList.getReservedListEntries().size()); reservedList.getName(), reservedList.getReservedListEntries().size());
} catch (Throwable t) {
logger.atSevere().withCause(t).log("Error saving the reserved list to Cloud SQL.");
}
} }
/** /**
@ -66,12 +65,10 @@ public class ReservedListDualWriteDao {
VKey.createOfy( VKey.createOfy(
ReservedList.class, ReservedList.class,
Key.create(getCrossTldKey(), ReservedList.class, reservedListName))); Key.create(getCrossTldKey(), ReservedList.class, reservedListName)));
try {
// Also load the list from Cloud SQL, compare the two lists, and log if different. // Also load the list from Cloud SQL, compare the two lists, and log if different.
maybeDatastoreList.ifPresent(ReservedListDualWriteDao::loadAndCompareCloudSqlList); DatabaseMigrationUtils.suppressExceptionUnlessInTest(
} catch (Throwable t) { () -> maybeDatastoreList.ifPresent(ReservedListDualDatabaseDao::loadAndCompareCloudSqlList),
logger.atSevere().withCause(t).log("Error comparing reserved lists."); "Error comparing reserved lists.");
}
return maybeDatastoreList; return maybeDatastoreList;
} }
@ -95,7 +92,7 @@ public class ReservedListDualWriteDao {
Maps.difference(datastoreLabelsToReservations, cloudSqlList.reservedListMap); Maps.difference(datastoreLabelsToReservations, cloudSqlList.reservedListMap);
if (!diff.areEqual()) { if (!diff.areEqual()) {
if (diff.entriesDiffering().size() > 10) { if (diff.entriesDiffering().size() > 10) {
logger.atWarning().log( throw new IllegalStateException(
String.format( String.format(
"Unequal reserved lists detected, Cloud SQL list with revision" "Unequal reserved lists detected, Cloud SQL list with revision"
+ " id %d has %d different records than the current" + " id %d has %d different records than the current"
@ -114,11 +111,11 @@ public class ReservedListDualWriteDao {
+ " %s in Cloud SQL.\n", + " %s in Cloud SQL.\n",
label, valueDiff.leftValue(), valueDiff.rightValue())); label, valueDiff.leftValue(), valueDiff.rightValue()));
}); });
logger.atWarning().log(diffMessage.toString()); throw new IllegalStateException(diffMessage.toString());
} }
} }
} else { } else {
logger.atWarning().log("Reserved list in Cloud SQL is empty."); throw new IllegalStateException("Reserved list in Cloud SQL is empty.");
} }
} }
} }

View file

@ -17,7 +17,7 @@ package google.registry.tools;
import com.beust.jcommander.Parameter; import com.beust.jcommander.Parameter;
import com.google.common.flogger.FluentLogger; import com.google.common.flogger.FluentLogger;
import google.registry.model.registry.label.ReservedList; import google.registry.model.registry.label.ReservedList;
import google.registry.model.registry.label.ReservedListDualWriteDao; import google.registry.model.registry.label.ReservedListDualDatabaseDao;
import google.registry.tools.params.PathParameter; import google.registry.tools.params.PathParameter;
import java.nio.file.Path; import java.nio.file.Path;
import javax.annotation.Nullable; import javax.annotation.Nullable;
@ -61,7 +61,7 @@ public abstract class CreateOrUpdateReservedListCommand extends MutatingCommand
name, reservedList.getReservedListEntries().size()); name, reservedList.getReservedListEntries().size());
try { try {
logger.atInfo().log("Saving reserved list for TLD %s", name); logger.atInfo().log("Saving reserved list for TLD %s", name);
ReservedListDualWriteDao.save(reservedList); ReservedListDualDatabaseDao.save(reservedList);
logger.atInfo().log(message); logger.atInfo().log(message);
} catch (Throwable e) { } catch (Throwable e) {
message = "Unexpected error saving reserved list from nomulus tool command"; message = "Unexpected error saving reserved list from nomulus tool command";

View file

@ -33,6 +33,7 @@ import static org.joda.money.CurrencyUnit.EUR;
import static org.joda.money.CurrencyUnit.USD; import static org.joda.money.CurrencyUnit.USD;
import static org.junit.jupiter.api.Assertions.assertThrows; import static org.junit.jupiter.api.Assertions.assertThrows;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableSet; import com.google.common.collect.ImmutableSet;
import com.google.common.collect.ImmutableSortedMap; import com.google.common.collect.ImmutableSortedMap;
import com.googlecode.objectify.Key; import com.googlecode.objectify.Key;
@ -135,9 +136,23 @@ public class RegistryTest extends EntityTestCase {
@TestOfyAndSql @TestOfyAndSql
void testSetReservedList_doesntMutateExistingRegistry() { void testSetReservedList_doesntMutateExistingRegistry() {
ReservedList rl15 = ReservedList rl15 =
persistReservedList("tld-reserved15", "potato,FULLY_BLOCKED", "phone,FULLY_BLOCKED"); persistReservedList(
new ReservedList.Builder()
.setName("tld-reserved15")
.setReservedListMapFromLines(
ImmutableList.of("potato,FULLY_BLOCKED", "phone,FULLY_BLOCKED"))
.setShouldPublish(true)
.setLastUpdateTime(fakeClock.nowUtc())
.build());
ReservedList rl16 = ReservedList rl16 =
persistReservedList("tld-reserved16", "port,FULLY_BLOCKED", "manteau,FULLY_BLOCKED"); persistReservedList(
new ReservedList.Builder()
.setName("tld-reserved16")
.setReservedListMapFromLines(
ImmutableList.of("port,FULLY_BLOCKED", "manteau,FULLY_BLOCKED"))
.setShouldPublish(true)
.setLastUpdateTime(fakeClock.nowUtc())
.build());
Registry registry1 = Registry registry1 =
newRegistry("propter", "PROPTER") newRegistry("propter", "PROPTER")
.asBuilder() .asBuilder()
@ -173,9 +188,23 @@ public class RegistryTest extends EntityTestCase {
@TestOfyAndSql @TestOfyAndSql
void testSetReservedLists() { void testSetReservedLists() {
ReservedList rl5 = ReservedList rl5 =
persistReservedList("tld-reserved5", "lol,FULLY_BLOCKED", "cat,FULLY_BLOCKED"); persistReservedList(
new ReservedList.Builder()
.setName("tld-reserved5")
.setReservedListMapFromLines(
ImmutableList.of("potato,FULLY_BLOCKED", "phone,FULLY_BLOCKED"))
.setShouldPublish(true)
.setLastUpdateTime(fakeClock.nowUtc())
.build());
ReservedList rl6 = ReservedList rl6 =
persistReservedList("tld-reserved6", "hammock,FULLY_BLOCKED", "mouse,FULLY_BLOCKED"); persistReservedList(
new ReservedList.Builder()
.setName("tld-reserved6")
.setReservedListMapFromLines(
ImmutableList.of("port,FULLY_BLOCKED", "manteau,FULLY_BLOCKED"))
.setShouldPublish(true)
.setLastUpdateTime(fakeClock.nowUtc())
.build());
Registry r = Registry r =
Registry.get("tld").asBuilder().setReservedLists(ImmutableSet.of(rl5, rl6)).build(); Registry.get("tld").asBuilder().setReservedLists(ImmutableSet.of(rl5, rl6)).build();
assertThat(r.getReservedLists().stream().map(Key::getName)) assertThat(r.getReservedLists().stream().map(Key::getName))
@ -186,15 +215,29 @@ public class RegistryTest extends EntityTestCase {
@TestOfyAndSql @TestOfyAndSql
void testSetReservedListsByName() { void testSetReservedListsByName() {
persistReservedList("tld-reserved24", "lol,FULLY_BLOCKED", "cat,FULLY_BLOCKED"); persistReservedList(
persistReservedList("tld-reserved25", "mit,FULLY_BLOCKED", "tim,FULLY_BLOCKED"); new ReservedList.Builder()
.setName("tld-reserved15")
.setReservedListMapFromLines(
ImmutableList.of("potato,FULLY_BLOCKED", "phone,FULLY_BLOCKED"))
.setShouldPublish(true)
.setLastUpdateTime(fakeClock.nowUtc())
.build());
persistReservedList(
new ReservedList.Builder()
.setName("tld-reserved16")
.setReservedListMapFromLines(
ImmutableList.of("port,FULLY_BLOCKED", "manteau,FULLY_BLOCKED"))
.setShouldPublish(true)
.setLastUpdateTime(fakeClock.nowUtc())
.build());
Registry r = Registry r =
Registry.get("tld") Registry.get("tld")
.asBuilder() .asBuilder()
.setReservedListsByName(ImmutableSet.of("tld-reserved24", "tld-reserved25")) .setReservedListsByName(ImmutableSet.of("tld-reserved15", "tld-reserved16"))
.build(); .build();
assertThat(r.getReservedLists().stream().map(Key::getName)) assertThat(r.getReservedLists().stream().map(Key::getName))
.containsExactly("tld-reserved24", "tld-reserved25"); .containsExactly("tld-reserved15", "tld-reserved16");
r = Registry.get("tld").asBuilder().setReservedListsByName(ImmutableSet.of()).build(); r = Registry.get("tld").asBuilder().setReservedListsByName(ImmutableSet.of()).build();
assertThat(r.getReservedLists()).isEmpty(); assertThat(r.getReservedLists()).isEmpty();
} }

View file

@ -105,6 +105,7 @@ import google.registry.model.registry.label.PremiumList.PremiumListEntry;
import google.registry.model.registry.label.PremiumList.PremiumListRevision; import google.registry.model.registry.label.PremiumList.PremiumListRevision;
import google.registry.model.registry.label.PremiumListDualDao; import google.registry.model.registry.label.PremiumListDualDao;
import google.registry.model.registry.label.ReservedList; import google.registry.model.registry.label.ReservedList;
import google.registry.model.registry.label.ReservedListDualDatabaseDao;
import google.registry.model.reporting.HistoryEntry; import google.registry.model.reporting.HistoryEntry;
import google.registry.model.transfer.ContactTransferData; import google.registry.model.transfer.ContactTransferData;
import google.registry.model.transfer.DomainTransferData; import google.registry.model.transfer.DomainTransferData;
@ -345,6 +346,13 @@ public class DatabaseHelper {
return persistReservedList(listName, true, lines); return persistReservedList(listName, true, lines);
} }
public static ReservedList persistReservedList(ReservedList reservedList) {
ReservedListDualDatabaseDao.save(reservedList);
maybeAdvanceClock();
tm().clearSessionCache();
return reservedList;
}
public static ReservedList persistReservedList( public static ReservedList persistReservedList(
String listName, boolean shouldPublish, String... lines) { String listName, boolean shouldPublish, String... lines) {
ReservedList reservedList = ReservedList reservedList =
@ -354,13 +362,7 @@ public class DatabaseHelper {
.setShouldPublish(shouldPublish) .setShouldPublish(shouldPublish)
.setLastUpdateTime(DateTime.now(DateTimeZone.UTC)) .setLastUpdateTime(DateTime.now(DateTimeZone.UTC))
.build(); .build();
return tm().isOfy() return persistReservedList(reservedList);
? persistResource(reservedList)
: tm().transact(
() -> {
tm().insert(reservedList);
return reservedList;
});
} }
/** /**

View file

@ -17,7 +17,7 @@ package google.registry.tools;
import static com.google.common.truth.Truth.assertThat; import static com.google.common.truth.Truth.assertThat;
import static com.google.common.truth.Truth8.assertThat; import static com.google.common.truth.Truth8.assertThat;
import static google.registry.model.registry.label.ReservationType.FULLY_BLOCKED; import static google.registry.model.registry.label.ReservationType.FULLY_BLOCKED;
import static google.registry.testing.DatabaseHelper.persistResource; import static google.registry.testing.DatabaseHelper.persistReservedList;
import static google.registry.util.DateTimeUtils.START_OF_TIME; import static google.registry.util.DateTimeUtils.START_OF_TIME;
import static org.junit.jupiter.api.Assertions.assertThrows; import static org.junit.jupiter.api.Assertions.assertThrows;
@ -35,11 +35,11 @@ class UpdateReservedListCommandTest
@BeforeEach @BeforeEach
void beforeEach() { void beforeEach() {
populateInitialReservedListInDatastore(true); populateInitialReservedListInDatabase(true);
} }
private void populateInitialReservedListInDatastore(boolean shouldPublish) { private void populateInitialReservedListInDatabase(boolean shouldPublish) {
persistResource( persistReservedList(
new ReservedList.Builder() new ReservedList.Builder()
.setName("xn--q9jyb4c_common-reserved") .setName("xn--q9jyb4c_common-reserved")
.setReservedListMapFromLines(ImmutableList.of("helicopter,FULLY_BLOCKED")) .setReservedListMapFromLines(ImmutableList.of("helicopter,FULLY_BLOCKED"))
@ -89,7 +89,7 @@ class UpdateReservedListCommandTest
@Test @Test
void testSuccess_shouldPublish_doesntOverrideFalseIfNotSpecified() throws Exception { void testSuccess_shouldPublish_doesntOverrideFalseIfNotSpecified() throws Exception {
populateInitialReservedListInDatastore(false); populateInitialReservedListInDatabase(false);
runCommandForced("--input=" + reservedTermsPath); runCommandForced("--input=" + reservedTermsPath);
assertThat(ReservedList.get("xn--q9jyb4c_common-reserved")).isPresent(); assertThat(ReservedList.get("xn--q9jyb4c_common-reserved")).isPresent();
ReservedList reservedList = ReservedList.get("xn--q9jyb4c_common-reserved").get(); ReservedList reservedList = ReservedList.get("xn--q9jyb4c_common-reserved").get();