Allow Entity instantiation without AppEngineRule (#559)

* Allow Entity instantiation without AppEngineRule

Defined an extension that sets up a fake AppEngine environment
so that Datastore entities can be instantiated.

* Allow Entity instantiation without AppEngineRule

Defined an extension that sets up a fake AppEngine environment
so that Datastore entities can be instantiated.
This commit is contained in:
Weimin Yu 2020-04-16 17:03:27 -04:00 committed by GitHub
parent 9b47a6cfee
commit 4f988d42c7
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 156 additions and 26 deletions

View file

@ -17,31 +17,44 @@ package google.registry.model.domain;
import static com.google.common.truth.Truth.assertThat;
import static google.registry.persistence.transaction.TransactionManagerFactory.jpaTm;
import static google.registry.util.DateTimeUtils.START_OF_TIME;
import static org.joda.time.DateTimeZone.UTC;
import com.google.common.collect.ImmutableSet;
import com.googlecode.objectify.Key;
import google.registry.model.EntityTestCase;
import google.registry.model.contact.ContactResource;
import google.registry.model.domain.DesignatedContact.Type;
import google.registry.model.domain.launch.LaunchNotice;
import google.registry.model.domain.secdns.DelegationSignerData;
import google.registry.model.eppcommon.AuthInfo.PasswordAuth;
import google.registry.model.eppcommon.StatusValue;
import google.registry.persistence.transaction.JpaTestRules;
import google.registry.persistence.transaction.JpaTestRules.JpaIntegrationWithCoverageExtension;
import google.registry.testing.DatastoreEntityExtension;
import google.registry.testing.FakeClock;
import javax.persistence.EntityManager;
import org.joda.time.DateTime;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Order;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.RegisterExtension;
/** Verify that we can store/retrieve DomainBase objects from a SQL database. */
public class DomainBaseSqlTest extends EntityTestCase {
public class DomainBaseSqlTest {
protected FakeClock fakeClock = new FakeClock(DateTime.now(UTC));
@RegisterExtension
@Order(value = 1)
DatastoreEntityExtension datastoreEntityExtension = new DatastoreEntityExtension();
@RegisterExtension
JpaIntegrationWithCoverageExtension jpa =
new JpaTestRules.Builder().withClock(fakeClock).buildIntegrationWithCoverageExtension();
DomainBase domain;
Key<ContactResource> contactKey;
Key<ContactResource> contact2Key;
public DomainBaseSqlTest() {
super(true);
}
@BeforeEach
public void setUp() {
contactKey = Key.create(ContactResource.class, "contact_id1");

View file

@ -16,27 +16,40 @@ package google.registry.schema.registrar;
import static com.google.common.truth.Truth.assertThat;
import static google.registry.persistence.transaction.TransactionManagerFactory.jpaTm;
import static org.joda.time.DateTimeZone.UTC;
import static org.junit.Assert.assertThrows;
import com.google.common.collect.ImmutableList;
import google.registry.model.EntityTestCase;
import google.registry.model.registrar.Registrar;
import google.registry.model.registrar.RegistrarAddress;
import google.registry.persistence.VKey;
import google.registry.persistence.transaction.JpaTestRules;
import google.registry.persistence.transaction.JpaTestRules.JpaIntegrationWithCoverageExtension;
import google.registry.testing.DatastoreEntityExtension;
import google.registry.testing.FakeClock;
import org.joda.time.DateTime;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Order;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.RegisterExtension;
/** Unit tests for persisting {@link Registrar} entities. */
public class RegistrarDaoTest extends EntityTestCase {
public class RegistrarDaoTest {
protected FakeClock fakeClock = new FakeClock(DateTime.now(UTC));
@RegisterExtension
@Order(value = 1)
DatastoreEntityExtension datastoreEntityExtension = new DatastoreEntityExtension();
@RegisterExtension
JpaIntegrationWithCoverageExtension jpa =
new JpaTestRules.Builder().withClock(fakeClock).buildIntegrationWithCoverageExtension();
private final VKey<Registrar> registrarKey = VKey.createSql(Registrar.class, "registrarId");
private Registrar testRegistrar;
public RegistrarDaoTest() {
super(true);
}
@BeforeEach
public void setUp() {
testRegistrar =

View file

@ -0,0 +1,104 @@
// Copyright 2020 The Nomulus Authors. All Rights Reserved.
//
// 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
//
// http://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 google.registry.testing;
import com.google.apphosting.api.ApiProxy;
import com.google.apphosting.api.ApiProxy.Environment;
import java.util.Map;
import org.junit.jupiter.api.extension.AfterEachCallback;
import org.junit.jupiter.api.extension.BeforeEachCallback;
import org.junit.jupiter.api.extension.ExtensionContext;
import org.testcontainers.shaded.com.google.common.collect.ImmutableMap;
/**
* Allows instantiation of Datastore {@code Entity entities} without the heavyweight {@code
* AppEngineRule}.
*
* <p>When used together with {@code JpaIntegrationWithCoverageExtension}, this extension must be
* registered first. For consistency's sake, it is recommended that the field for this extension be
* annotated with {@code @org.junit.jupiter.api.Order(value = 1)}. Please refer to {@link
* google.registry.model.domain.DomainBaseSqlTest} for example, and to <a
* href="https://junit.org/junit5/docs/current/user-guide/#extensions-registration-programmatic">
* JUnit 5 User Guide</a> for details of extension ordering.
*/
public class DatastoreEntityExtension implements BeforeEachCallback, AfterEachCallback {
private static final Environment PLACEHOLDER_ENV = new PlaceholderEnvironment();
@Override
public void beforeEach(ExtensionContext context) {
ApiProxy.setEnvironmentForCurrentThread(PLACEHOLDER_ENV);
}
@Override
public void afterEach(ExtensionContext context) {
// Clear the cached instance.
ApiProxy.setEnvironmentForCurrentThread(null);
}
private static final class PlaceholderEnvironment implements Environment {
@Override
public String getAppId() {
return "PlaceholderAppId";
}
@Override
public Map<String, Object> getAttributes() {
return ImmutableMap.of();
}
@Override
public String getModuleId() {
throw new UnsupportedOperationException();
}
@Override
public String getVersionId() {
throw new UnsupportedOperationException();
}
@Override
public String getEmail() {
throw new UnsupportedOperationException();
}
@Override
public boolean isLoggedIn() {
throw new UnsupportedOperationException();
}
@Override
public boolean isAdmin() {
throw new UnsupportedOperationException();
}
@Override
public String getAuthDomain() {
throw new UnsupportedOperationException();
}
@SuppressWarnings("deprecation")
@Override
public String getRequestNamespace() {
throw new UnsupportedOperationException();
}
@Override
public long getRemainingMillis() {
throw new UnsupportedOperationException();
}
}
}

View file

@ -18,21 +18,19 @@ import static com.google.common.truth.Truth.assertThat;
import static java.nio.charset.StandardCharsets.UTF_8;
import com.google.common.io.Resources;
import google.registry.testing.AppEngineRule;
import google.registry.testing.DatastoreEntityExtension;
import google.registry.tools.LevelDbFileBuilder.Property;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.io.PrintStream;
import java.net.URL;
import org.junit.After;
import org.junit.Before;
import org.junit.Rule;
import org.junit.Test;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.RegisterExtension;
import org.junit.rules.TemporaryFolder;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;
@RunWith(JUnit4.class)
public class CompareDbBackupsTest {
private static final int BASE_ID = 1001;
@ -41,20 +39,22 @@ public class CompareDbBackupsTest {
private final ByteArrayOutputStream stdout = new ByteArrayOutputStream();
private PrintStream orgStdout;
@Rule public final TemporaryFolder tempFs = new TemporaryFolder();
public final TemporaryFolder tempFs = new TemporaryFolder();
@Rule
public final AppEngineRule appEngine = AppEngineRule.builder().withDatastoreAndCloudSql().build();
@RegisterExtension
public DatastoreEntityExtension datastoreEntityExtension = new DatastoreEntityExtension();
@Before
public void before() {
@BeforeEach
public void before() throws IOException {
orgStdout = System.out;
System.setOut(new PrintStream(stdout));
tempFs.create();
}
@After
@AfterEach
public void after() {
System.setOut(orgStdout);
tempFs.delete();
}
@Test