From b7a0b6ec6aff776611e0d4b017377279976cd2cd Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Mon, 30 Sep 2019 17:18:31 +0300 Subject: [PATCH 01/30] Init `testutil-gcloud` module --- build.gradle | 2 +- config | 2 +- settings.gradle | 1 + testutil-gcloud/build.gradle | 22 ++++++++++++++++++++++ 4 files changed, 25 insertions(+), 2 deletions(-) create mode 100644 testutil-gcloud/build.gradle diff --git a/build.gradle b/build.gradle index ba9e9bd44..615d4f43e 100644 --- a/build.gradle +++ b/build.gradle @@ -44,7 +44,7 @@ ext { credentialsPropertyFile = 'credentials.properties' spineProtobufPluginId = 'io.spine.tools.spine-model-compiler' - projectsToPublish = ['datastore', 'stackdriver-trace'] + projectsToPublish = ['datastore', 'stackdriver-trace', 'testutil-gcloud'] } allprojects { diff --git a/config b/config index 5c31b0830..dbb44338d 160000 --- a/config +++ b/config @@ -1 +1 @@ -Subproject commit 5c31b083088b5ce66223a9b09639d5a33a7b8b84 +Subproject commit dbb44338da3564cfa75a31a021a074aee3b62d00 diff --git a/settings.gradle b/settings.gradle index 99fcd5b56..1bdb8a9c4 100644 --- a/settings.gradle +++ b/settings.gradle @@ -22,3 +22,4 @@ rootProject.name = 'spine-gcloud-java' include 'datastore' include 'stackdriver-trace' +include 'testutil-gcloud' diff --git a/testutil-gcloud/build.gradle b/testutil-gcloud/build.gradle new file mode 100644 index 000000000..1e1ac6425 --- /dev/null +++ b/testutil-gcloud/build.gradle @@ -0,0 +1,22 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +dependencies { +} From e62da411df1d9a9fc45c23ad5c7e1d2d29b4e270 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Mon, 30 Sep 2019 20:52:39 +0300 Subject: [PATCH 02/30] Extract `gcloud` test utils to `testutil-gcloud` module --- datastore/build.gradle | 1 + .../datastore/DatastoreStorageFactory.java | 2 +- .../storage/datastore/DatastoreWrapper.java | 10 +- .../DatastoreStorageFactoryBuilderTest.java | 4 +- .../DatastoreStorageFactoryTest.java | 9 +- .../datastore/DatastoreWrapperTest.java | 12 +- ...AggregateStorageLifecycleHandlingTest.java | 5 +- .../datastore/DsAggregateStorageTest.java | 8 +- .../DsAggregateStorageTruncationTest.java | 1 + .../storage/datastore/DsInboxStorageTest.java | 1 + .../datastore/DsProjectionStorageTest.java | 5 +- .../datastore/DsPropertyStorageTest.java | 5 +- .../datastore/DsRecordStorageTest.java | 7 +- .../datastore/DsShardedWorkRegistryTest.java | 1 + .../server/storage/datastore/IndexesTest.java | 3 +- .../NewBoundedContextBuilderTest.java | 2 +- .../storage/datastore/ProjectIdTest.java | 5 +- .../given/DatastoreWrapperTestEnv.java | 1 + .../given/DsRecordStorageTestEnv.java | 2 +- .../tenant/DatastoreTenantsTest.java | 2 +- .../tenant/NamespaceConvertersTest.java | 2 +- .../datastore/tenant/NamespaceIndexTest.java | 13 +- .../datastore/tenant/NamespaceTest.java | 2 +- .../datastore/type/DsColumnTypesTest.java | 2 +- license-report.md | 764 +++++++++++++++++- testutil-gcloud/build.gradle | 2 + .../storage/datastore/BigDataTester.java | 19 +- .../datastore}/CountingDatastoreWrapper.java | 3 +- .../storage/datastore/SpyStorageFactory.java | 14 +- .../TestDatastoreStorageFactory.java | 10 +- .../datastore/TestDatastoreWrapper.java | 18 +- .../storage/datastore}/TestDatastores.java | 5 +- .../storage/datastore}/TestEnvironment.java | 2 +- .../datastore/TestNamespaceSuppliers.java | 38 + .../storage/datastore/package-info.java | 31 + 35 files changed, 931 insertions(+), 80 deletions(-) rename {datastore/src/test/java/io/spine => testutil-gcloud/src/main/java/io/spine/testing}/server/storage/datastore/BigDataTester.java (92%) rename {datastore/src/test/java/io/spine/server/storage/datastore/given => testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore}/CountingDatastoreWrapper.java (96%) rename {datastore/src/test/java/io/spine => testutil-gcloud/src/main/java/io/spine/testing}/server/storage/datastore/SpyStorageFactory.java (78%) rename {datastore/src/test/java/io/spine => testutil-gcloud/src/main/java/io/spine/testing}/server/storage/datastore/TestDatastoreStorageFactory.java (94%) rename {datastore/src/test/java/io/spine => testutil-gcloud/src/main/java/io/spine/testing}/server/storage/datastore/TestDatastoreWrapper.java (90%) rename {datastore/src/test/java/io/spine/server/storage/datastore/given => testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore}/TestDatastores.java (97%) rename {datastore/src/test/java/io/spine/server/storage/datastore/given => testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore}/TestEnvironment.java (97%) create mode 100644 testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java create mode 100644 testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/package-info.java diff --git a/datastore/build.gradle b/datastore/build.gradle index 1c8e9a0c2..f411d5ce3 100644 --- a/datastore/build.gradle +++ b/datastore/build.gradle @@ -29,6 +29,7 @@ dependencies { exclude group: 'com.google.guava' } + testImplementation project(path: ":testutil-gcloud") testImplementation "io.spine:spine-server:" } diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java index e9b80b026..78cea9190 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java @@ -90,7 +90,7 @@ public class DatastoreStorageFactory implements StorageFactory { private final NsConverterFactory converterFactory; - DatastoreStorageFactory(Builder builder) { + protected DatastoreStorageFactory(Builder builder) { this.typeRegistry = builder.typeRegistry; this.datastore = builder.datastore; this.converterFactory = builder.converterFactory; diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java index e7377925b..4819f8ed5 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java @@ -301,7 +301,7 @@ public DsQueryIterator read(StructuredQuery query) { * @throws IllegalArgumentException * if the provided {@linkplain StructuredQuery#getLimit() query includes a limit} */ - Iterator readAll(StructuredQuery query, int pageSize) { + public Iterator readAll(StructuredQuery query, int pageSize) { return readAllPageByPage(query, pageSize); } @@ -322,7 +322,7 @@ Iterator readAll(StructuredQuery query, int pageSize) { * @throws IllegalArgumentException * if the provided {@linkplain StructuredQuery#getLimit() query includes a limit} */ - Iterator readAll(StructuredQuery query) { + public Iterator readAll(StructuredQuery query) { return readAllPageByPage(query, null); } @@ -386,7 +386,8 @@ public void delete(Key... keys) { * @param table * kind (a.k.a. type, table, etc.) of the records to delete */ - void dropTable(String table) { + @VisibleForTesting + protected void dropTable(String table) { Namespace namespace = currentNamespace(); StructuredQuery query = Query.newEntityQueryBuilder() @@ -522,7 +523,8 @@ public DatastoreOptions datastoreOptions() { return options; } - Datastore datastore() { + @VisibleForTesting + public Datastore datastore() { return datastore; } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java index 016e4e313..c2103741d 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java @@ -27,8 +27,8 @@ import io.spine.server.entity.storage.ColumnType; import io.spine.server.entity.storage.ColumnTypeRegistry; import io.spine.server.storage.datastore.given.Columns.ByteColumnType; -import io.spine.server.storage.datastore.given.TestDatastores; import io.spine.server.storage.datastore.type.DatastoreTypeRegistryFactory; +import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Nested; @@ -36,11 +36,11 @@ import static io.spine.server.ContextSpec.singleTenant; import static io.spine.server.storage.datastore.given.Columns.byteColumn; -import static io.spine.server.storage.datastore.given.TestDatastores.projectId; import static io.spine.server.storage.datastore.type.DatastoreTypeRegistryFactory.predefinedValuesAnd; import static io.spine.testing.DisplayNames.HAVE_PARAMETERLESS_CTOR; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; import static io.spine.testing.Tests.assertHasPrivateParameterlessCtor; +import static io.spine.testing.server.storage.datastore.TestDatastores.projectId; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertThrows; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java index 57a0e502c..4e11fcd9d 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java @@ -35,19 +35,19 @@ import io.spine.server.entity.storage.ColumnTypeRegistry; import io.spine.server.storage.RecordStorage; import io.spine.server.storage.StorageFactory; -import io.spine.server.storage.datastore.given.TestEnvironment; import io.spine.server.storage.datastore.type.DatastoreTypeRegistryFactory; import io.spine.test.storage.Project; +import io.spine.testing.server.storage.datastore.TestEnvironment; import io.spine.type.TypeName; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; import static com.google.common.truth.Truth.assertThat; import static io.spine.server.ContextSpec.multitenant; -import static io.spine.server.storage.datastore.given.TestDatastores.local; -import static io.spine.server.storage.datastore.given.TestDatastores.projectId; import static io.spine.server.tenant.TenantAwareRunner.with; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; +import static io.spine.testing.server.storage.datastore.TestDatastores.local; +import static io.spine.testing.server.storage.datastore.TestDatastores.projectId; import static org.junit.jupiter.api.Assertions.assertNotEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertSame; @@ -81,7 +81,8 @@ void testCreateMultitenant() { StorageFactory factory = DatastoreStorageFactory.newBuilder() .setDatastore(datastore) .build(); - RecordStorage storage = factory.createRecordStorage(TestEnvironment.multiTenantSpec(), TestEntity.class); + RecordStorage storage = + factory.createRecordStorage(TestEnvironment.multiTenantSpec(), TestEntity.class); assertTrue(storage.isMultitenant()); storage.close(); } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java index 97ddbbeb6..718912e76 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java @@ -29,8 +29,8 @@ import io.spine.core.TenantId; import io.spine.net.EmailAddress; import io.spine.net.InternetDomain; -import io.spine.server.storage.datastore.given.TestDatastores; import io.spine.server.tenant.TenantAwareFunction0; +import io.spine.testing.server.storage.datastore.TestDatastoreWrapper; import org.junit.jupiter.api.AfterAll; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; @@ -48,16 +48,17 @@ import static com.google.cloud.datastore.Query.newEntityQueryBuilder; import static com.google.common.collect.Lists.newArrayList; import static com.google.common.truth.Truth.assertThat; -import static io.spine.server.storage.datastore.TestDatastoreWrapper.wrap; +import static io.spine.server.storage.datastore.DatastoreWrapper.wrap; import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.GENERIC_ENTITY_KIND; import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.NAMESPACE_HOLDER_KIND; import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.checkTenantIdInKey; import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.ensureNamespace; import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.localDatastore; import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.remoteDatastore; -import static io.spine.server.storage.datastore.given.TestEnvironment.runsOnCi; import static io.spine.server.storage.datastore.tenant.TestNamespaceSuppliers.multitenant; import static io.spine.server.storage.datastore.tenant.TestNamespaceSuppliers.singleTenant; +import static io.spine.testing.server.storage.datastore.TestDatastoreWrapper.wrap; +import static io.spine.testing.server.storage.datastore.TestEnvironment.runsOnCi; import static java.lang.String.format; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertFalse; @@ -318,6 +319,8 @@ void tearDown() { wrapper.dropAllTables(); } + @SuppressWarnings({"CheckReturnValue", "ResultOfMethodCallIgnored"}) + // Called to throw exception. @Test @DisplayName("throws IAE during batch read with limit") void testIaeOnBatchReadWithLimit() { @@ -327,6 +330,8 @@ void testIaeOnBatchReadWithLimit() { .build(), 1)); } + @SuppressWarnings({"CheckReturnValue", "ResultOfMethodCallIgnored"}) + // Called to throw exception. @Test @DisplayName("throws IAE during batch read of 0 size") void testIaeOnBatchReadWithZeroSize() { @@ -338,7 +343,6 @@ void testIaeOnBatchReadWithZeroSize() { @Test @DisplayName("generate key factories aware of tenancy") void testGenerateKeyFactory() { - ProjectId projectId = TestDatastores.projectId(); DatastoreWrapper wrapper = wrap(localDatastore(), multitenant()); String tenantId1 = "first-tenant-ID"; String tenantId1Prefixed = "Vfirst-tenant-ID"; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java index 4fadf85b1..cac7e8125 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java @@ -24,13 +24,14 @@ import io.spine.server.aggregate.AggregateStorage; import io.spine.server.aggregate.AggregateStorageLifecycleFlagsHandlingTest; import io.spine.test.aggregate.ProjectId; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import org.junit.jupiter.api.AfterAll; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeAll; import org.junit.jupiter.api.DisplayName; -import static io.spine.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; -import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; +import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; +import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; @DisplayName("`DsAggregateStorage` lifecycle handling should") class DsAggregateStorageLifecycleHandlingTest diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java index 46bfff463..debc2d032 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java @@ -40,7 +40,6 @@ import io.spine.server.aggregate.Snapshot; import io.spine.server.aggregate.given.repo.ProjectAggregate; import io.spine.server.entity.Entity; -import io.spine.server.storage.datastore.given.CountingDatastoreWrapper; import io.spine.server.storage.datastore.given.aggregate.ProjectAggregateRepository; import io.spine.server.type.CommandEnvelope; import io.spine.test.aggregate.Project; @@ -50,6 +49,9 @@ import io.spine.testdata.Sample; import io.spine.testing.client.TestActorRequestFactory; import io.spine.testing.server.TestEventFactory; +import io.spine.testing.server.storage.datastore.CountingDatastoreWrapper; +import io.spine.testing.server.storage.datastore.SpyStorageFactory; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import org.junit.jupiter.api.AfterAll; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeAll; @@ -68,9 +70,9 @@ import static io.spine.server.ContextSpec.singleTenant; import static io.spine.server.aggregate.given.Given.CommandMessage.addTask; import static io.spine.server.storage.datastore.DatastoreWrapper.MAX_ENTITIES_PER_WRITE_REQUEST; -import static io.spine.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.datastoreFactory; -import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; +import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; +import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertNull; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTruncationTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTruncationTest.java index 983a764d5..b249155b6 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTruncationTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTruncationTest.java @@ -22,6 +22,7 @@ import io.spine.server.aggregate.AggregateStorageTruncationTest; import io.spine.server.storage.StorageFactory; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import org.junit.jupiter.api.DisplayName; @DisplayName("`DsAggregateStorage` after truncation should") diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsInboxStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsInboxStorageTest.java index 4791d28c5..c7c1a1935 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsInboxStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsInboxStorageTest.java @@ -35,6 +35,7 @@ import io.spine.server.delivery.Page; import io.spine.server.delivery.ShardIndex; import io.spine.server.storage.datastore.given.DsInboxStorageTestEnv; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.DisplayName; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java index d7052145b..afd8f0070 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java @@ -31,12 +31,13 @@ import io.spine.test.storage.Project; import io.spine.test.storage.ProjectId; import io.spine.testdata.Sample; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.DisplayName; import static io.spine.base.Time.currentTime; -import static io.spine.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; -import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; +import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; +import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; @DisplayName("`DsProjectionStorage` should") class DsProjectionStorageTest extends ProjectionStorageTest { diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java index a2ab18667..648bd6f7b 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java @@ -19,11 +19,12 @@ */ package io.spine.server.storage.datastore; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; -import static io.spine.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; -import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; +import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; +import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; import static org.junit.jupiter.api.Assertions.assertNotNull; @DisplayName("`DsPropertyStorage` should") diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java index ef14dd979..8042c9740 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java @@ -44,7 +44,6 @@ import io.spine.server.storage.RecordStorageTest; import io.spine.server.storage.StorageFactory; import io.spine.server.storage.datastore.given.CollegeEntity; -import io.spine.server.storage.datastore.given.CountingDatastoreWrapper; import io.spine.server.storage.datastore.given.DsRecordStorageTestEnv; import io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.EntityWithCustomColumnName; import io.spine.server.storage.datastore.given.TestConstCounterEntity; @@ -54,6 +53,10 @@ import io.spine.test.storage.Project; import io.spine.test.storage.ProjectId; import io.spine.test.storage.Task; +import io.spine.testing.server.storage.datastore.BigDataTester; +import io.spine.testing.server.storage.datastore.CountingDatastoreWrapper; +import io.spine.testing.server.storage.datastore.SpyStorageFactory; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import io.spine.type.TypeUrl; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; @@ -114,7 +117,7 @@ import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.recordIds; import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.sortedIds; import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.sortedValues; -import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; +import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; import static java.util.Collections.singletonList; import static java.util.stream.Collectors.toList; import static org.junit.Assert.assertFalse; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsShardedWorkRegistryTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsShardedWorkRegistryTest.java index dd8d36bd2..7a4afdfde 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsShardedWorkRegistryTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsShardedWorkRegistryTest.java @@ -30,6 +30,7 @@ import io.spine.server.delivery.ShardSessionRecord; import io.spine.server.delivery.ShardedWorkRegistry; import io.spine.server.delivery.ShardedWorkRegistryTest; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.DisplayName; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/IndexesTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/IndexesTest.java index 2f38b596e..3078608b9 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/IndexesTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/IndexesTest.java @@ -21,7 +21,8 @@ package io.spine.server.storage.datastore; import com.google.common.testing.NullPointerTester; -import io.spine.server.storage.datastore.given.TestDatastores; +import io.spine.testing.server.storage.datastore.TestDatastoreWrapper; +import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/NewBoundedContextBuilderTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/NewBoundedContextBuilderTest.java index 55bc2cff7..ed377c5b9 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/NewBoundedContextBuilderTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/NewBoundedContextBuilderTest.java @@ -23,9 +23,9 @@ import com.google.cloud.datastore.Datastore; import io.spine.server.BoundedContext; import io.spine.server.BoundedContextBuilder; -import io.spine.server.storage.datastore.given.TestDatastores; import io.spine.server.storage.datastore.tenant.TestNamespaceIndex; import io.spine.server.tenant.TenantIndex; +import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/ProjectIdTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/ProjectIdTest.java index b7001d314..5d7682a95 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/ProjectIdTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/ProjectIdTest.java @@ -24,13 +24,12 @@ import com.google.cloud.datastore.DatastoreOptions; import com.google.common.testing.EqualsTester; import com.google.common.testing.NullPointerTester; -import io.spine.server.storage.datastore.given.TestDatastores; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; import static com.google.common.truth.Truth.assertThat; -import static io.spine.server.storage.datastore.given.TestDatastores.local; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; +import static io.spine.testing.server.storage.datastore.TestDatastores.local; @DisplayName("`ProjectId` should") class ProjectIdTest { @@ -39,7 +38,7 @@ class ProjectIdTest { @DisplayName(NOT_ACCEPT_NULLS) void testNulls() { new NullPointerTester() - .setDefault(Datastore.class, TestDatastores.local()) + .setDefault(Datastore.class, local()) .testStaticMethods(ProjectId.class, NullPointerTester.Visibility.PACKAGE); } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java b/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java index e9aff5396..022c62a35 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java @@ -28,6 +28,7 @@ import io.spine.server.storage.datastore.DatastoreWrapper; import io.spine.server.storage.datastore.Kind; import io.spine.server.tenant.TenantAwareOperation; +import io.spine.testing.server.storage.datastore.TestDatastores; import static org.junit.jupiter.api.Assertions.assertEquals; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/given/DsRecordStorageTestEnv.java b/datastore/src/test/java/io/spine/server/storage/datastore/given/DsRecordStorageTestEnv.java index b238ef713..f8d9ffade 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/given/DsRecordStorageTestEnv.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/given/DsRecordStorageTestEnv.java @@ -38,11 +38,11 @@ import io.spine.server.entity.storage.Column; import io.spine.server.entity.storage.EntityRecordWithColumns; import io.spine.server.storage.RecordStorage; -import io.spine.server.storage.datastore.TestDatastoreStorageFactory; import io.spine.test.datastore.College; import io.spine.test.datastore.CollegeId; import io.spine.test.storage.Project; import io.spine.test.storage.ProjectId; +import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import java.security.SecureRandom; import java.util.ArrayList; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/DatastoreTenantsTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/DatastoreTenantsTest.java index 364075aa4..423cb6b8f 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/DatastoreTenantsTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/DatastoreTenantsTest.java @@ -21,8 +21,8 @@ package io.spine.server.storage.datastore.tenant; import io.spine.core.TenantId; -import io.spine.server.storage.datastore.given.TestDatastores; import io.spine.server.tenant.TenantIndex; +import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceConvertersTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceConvertersTest.java index 23b205878..3525e0f06 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceConvertersTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceConvertersTest.java @@ -33,7 +33,7 @@ class NamespaceConvertersTest { @Test @DisplayName(HAVE_PARAMETERLESS_CTOR) - void have_private_utility_ctor() { + void haveUtilityCtor() { assertHasPrivateParameterlessCtor(NamespaceConverters.class); } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceIndexTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceIndexTest.java index f8c9221a6..719ededf2 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceIndexTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceIndexTest.java @@ -34,10 +34,10 @@ import io.spine.server.entity.EntityRecord; import io.spine.server.storage.RecordStorage; import io.spine.server.storage.datastore.DatastoreStorageFactory; -import io.spine.server.storage.datastore.given.TestDatastores; import io.spine.server.storage.datastore.tenant.given.TestProjection; import io.spine.test.datastore.College; import io.spine.testing.TestValues; +import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.DisplayName; @@ -53,7 +53,6 @@ import static com.google.common.base.Throwables.getStackTraceAsString; import static com.google.common.truth.Truth.assertThat; import static io.spine.protobuf.AnyPacker.pack; -import static io.spine.server.storage.datastore.given.TestDatastores.local; import static io.spine.server.tenant.TenantAwareRunner.with; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; import static java.lang.String.format; @@ -297,10 +296,12 @@ private static Key key(String name) { private static Datastore datastore() { String namespace = "Vsome-namespace"; - DatastoreOptions options = local().getOptions() - .toBuilder() - .setNamespace(namespace) - .build(); + DatastoreOptions options = TestDatastores + .local() + .getOptions() + .toBuilder() + .setNamespace(namespace) + .build(); Datastore datastore = options.getService(); return datastore; } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java index fd6b39be1..5196417b4 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java @@ -27,7 +27,7 @@ import io.spine.net.EmailAddress; import io.spine.net.InternetDomain; import io.spine.server.storage.datastore.ProjectId; -import io.spine.server.storage.datastore.given.TestDatastores; +import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java index 412252512..fe3a441c4 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java @@ -28,9 +28,9 @@ import io.spine.core.Version; import io.spine.core.Versions; import io.spine.json.Json; -import io.spine.server.storage.datastore.given.TestDatastores; import io.spine.test.storage.Project; import io.spine.testdata.Sample; +import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/license-report.md b/license-report.md index ecea747de..048e502de 100644 --- a/license-report.md +++ b/license-report.md @@ -734,7 +734,7 @@ The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Thu Sep 26 15:14:26 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Mon Sep 30 20:28:12 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -1474,4 +1474,764 @@ This report was generated on **Thu Sep 26 15:14:26 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Thu Sep 26 15:14:38 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file +This report was generated on **Mon Sep 30 20:28:25 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). + + + + +# Dependencies of `io.spine.gcloud:spine-testutil-gcloud:1.1.2` + +## Runtime +1. **Group:** com.fasterxml.jackson.core **Name:** jackson-core **Version:** 2.9.9 + * **Project URL:** [https://github.com/FasterXML/jackson-core](https://github.com/FasterXML/jackson-core) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.android **Name:** annotations **Version:** 4.1.1.4 + * **POM Project URL:** [http://source.android.com/](http://source.android.com/) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0](http://www.apache.org/licenses/LICENSE-2.0) + +1. **Group:** com.google.api **Name:** api-common **Version:** 1.8.1 + * **POM Project URL:** [https://github.com/googleapis/api-common-java](https://github.com/googleapis/api-common-java) + * **POM License: BSD** - [https://github.com/googleapis/api-common-java/blob/master/LICENSE](https://github.com/googleapis/api-common-java/blob/master/LICENSE) + +1. **Group:** com.google.api **Name:** gax **Version:** 1.48.1 + * **POM Project URL:** [https://github.com/googleapis/gax-java](https://github.com/googleapis/gax-java) + * **POM License: BSD** - [https://github.com/googleapis/gax-java/blob/master/LICENSE](https://github.com/googleapis/gax-java/blob/master/LICENSE) + +1. **Group:** com.google.api **Name:** gax-httpjson **Version:** 0.65.1 + * **POM Project URL:** [https://github.com/googleapis/gax-java](https://github.com/googleapis/gax-java) + * **POM License: BSD** - [https://github.com/googleapis/gax-java/blob/master/LICENSE](https://github.com/googleapis/gax-java/blob/master/LICENSE) + +1. **Group:** com.google.api-client **Name:** google-api-client **Version:** 1.30.2 + * **Manifest Project URL:** [https://developers.google.com/api-client-library/java/](https://developers.google.com/api-client-library/java/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.api.grpc **Name:** proto-google-cloud-datastore-v1 **Version:** 0.74.0 + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.api.grpc **Name:** proto-google-common-protos **Version:** 1.16.0 + * **POM Project URL:** [https://github.com/googleapis/common-protos-java](https://github.com/googleapis/common-protos-java) + * **POM License: Apache** - [https://github.com/googleapis/common-protos-java/blob/master/LICENSE](https://github.com/googleapis/common-protos-java/blob/master/LICENSE) + +1. **Group:** com.google.api.grpc **Name:** proto-google-iam-v1 **Version:** 0.12.0 + * **POM Project URL:** [https://github.com/googleapis/api-client-staging](https://github.com/googleapis/api-client-staging) + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.auth **Name:** google-auth-library-credentials **Version:** 0.17.1 + * **POM License: BSD New license** - [http://opensource.org/licenses/BSD-3-Clause](http://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.google.auth **Name:** google-auth-library-oauth2-http **Version:** 0.17.1 + * **POM License: BSD New license** - [http://opensource.org/licenses/BSD-3-Clause](http://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.google.auto.value **Name:** auto-value-annotations **Version:** 1.6.6 + * **POM Project URL:** [https://github.com/google/auto/tree/master/value](https://github.com/google/auto/tree/master/value) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.cloud **Name:** google-cloud-core **Version:** 1.90.0 + * **POM Project URL:** [https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-core](https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-core) + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.cloud **Name:** google-cloud-core-http **Version:** 1.90.0 + * **POM Project URL:** [https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-core-http](https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-core-http) + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.cloud **Name:** google-cloud-datastore **Version:** 1.91.0 + * **POM Project URL:** [https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-datastore](https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-datastore) + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.cloud.datastore **Name:** datastore-v1-proto-client **Version:** 1.6.0 + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.code.findbugs **Name:** jsr305 **Version:** 3.0.2 + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM Project URL:** [http://findbugs.sourceforge.net/](http://findbugs.sourceforge.net/) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.code.gson **Name:** gson **Version:** 2.8.5 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.errorprone **Name:** error_prone_annotations **Version:** 2.3.3 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.errorprone **Name:** error_prone_type_annotations **Version:** 2.3.3 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.flogger **Name:** flogger **Version:** 0.4 + * **POM Project URL:** [https://github.com/google/flogger](https://github.com/google/flogger) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.flogger **Name:** flogger-system-backend **Version:** 0.4 + * **POM Project URL:** [https://github.com/google/flogger](https://github.com/google/flogger) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.guava **Name:** failureaccess **Version:** 1.0.1 + * **Manifest Project URL:** [https://github.com/google/guava/](https://github.com/google/guava/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.guava **Name:** guava **Version:** 28.1-jre + * **Manifest Project URL:** [https://github.com/google/guava/](https://github.com/google/guava/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.guava **Name:** listenablefuture **Version:** 9999.0-empty-to-avoid-conflict-with-guava + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client **Version:** 1.31.0 + * **Manifest Project URL:** [http://www.google.com/](http://www.google.com/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client-appengine **Version:** 1.31.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client-jackson **Version:** 1.20.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client-jackson2 **Version:** 1.31.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client-protobuf **Version:** 1.20.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.j2objc **Name:** j2objc-annotations **Version:** 1.3 + * **POM Project URL:** [https://github.com/google/j2objc/](https://github.com/google/j2objc/) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.oauth-client **Name:** google-oauth-client **Version:** 1.30.1 + * **Manifest Project URL:** [http://www.google.com/](http://www.google.com/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.protobuf **Name:** protobuf-java **Version:** 3.9.0 + * **Manifest Project URL:** [https://developers.google.com/protocol-buffers/](https://developers.google.com/protocol-buffers/) + * **Manifest license URL:** [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + * **POM License: 3-Clause BSD License** - [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.google.protobuf **Name:** protobuf-java-util **Version:** 3.9.0 + * **Manifest Project URL:** [https://developers.google.com/protocol-buffers/](https://developers.google.com/protocol-buffers/) + * **Manifest license URL:** [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + * **POM License: 3-Clause BSD License** - [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.squareup.okhttp **Name:** okhttp **Version:** 2.5.0 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.squareup.okio **Name:** okio **Version:** 1.13.0 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** commons-codec **Name:** commons-codec **Version:** 1.11 + * **Project URL:** [http://commons.apache.org/proper/commons-codec/](http://commons.apache.org/proper/commons-codec/) + * **Manifest license URL:** [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: Apache License, Version 2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** commons-logging **Name:** commons-logging **Version:** 1.2 + * **Project URL:** [http://commons.apache.org/proper/commons-logging/](http://commons.apache.org/proper/commons-logging/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** io.grpc **Name:** grpc-api **Version:** 1.23.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-context **Version:** 1.23.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-core **Version:** 1.23.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-okhttp **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-protobuf **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-protobuf-lite **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-stub **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.opencensus **Name:** opencensus-api **Version:** 0.23.0 + * **POM Project URL:** [https://github.com/census-instrumentation/opencensus-java](https://github.com/census-instrumentation/opencensus-java) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** io.opencensus **Name:** opencensus-contrib-grpc-metrics **Version:** 0.21.0 + * **POM Project URL:** [https://github.com/census-instrumentation/opencensus-java](https://github.com/census-instrumentation/opencensus-java) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** io.opencensus **Name:** opencensus-contrib-http-util **Version:** 0.21.0 + * **POM Project URL:** [https://github.com/census-instrumentation/opencensus-java](https://github.com/census-instrumentation/opencensus-java) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** io.perfmark **Name:** perfmark-api **Version:** 0.17.0 + * **POM Project URL:** [https://github.com/perfmark/perfmark](https://github.com/perfmark/perfmark) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** javax.annotation **Name:** javax.annotation-api **Version:** 1.3.2 + * **Manifest Project URL:** [https://javaee.github.io/glassfish](https://javaee.github.io/glassfish) + * **Manifest license URL:** [https://github.com/javaee/javax.annotation/blob/master/LICENSE](https://github.com/javaee/javax.annotation/blob/master/LICENSE) + * **POM Project URL:** [http://jcp.org/en/jsr/detail?id=250](http://jcp.org/en/jsr/detail?id=250) + * **POM License: CDDL + GPLv2 with classpath exception** - [https://github.com/javaee/javax.annotation/blob/master/LICENSE](https://github.com/javaee/javax.annotation/blob/master/LICENSE) + +1. **Group:** org.apache.httpcomponents **Name:** httpclient **Version:** 4.5.9 + * **POM Project URL:** [http://hc.apache.org/httpcomponents-client](http://hc.apache.org/httpcomponents-client) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.apache.httpcomponents **Name:** httpcore **Version:** 4.4.11 + * **POM Project URL:** [http://hc.apache.org/httpcomponents-core-ga](http://hc.apache.org/httpcomponents-core-ga) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.apiguardian **Name:** apiguardian-api **Version:** 1.1.0 + * **POM Project URL:** [https://github.com/apiguardian-team/apiguardian](https://github.com/apiguardian-team/apiguardian) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.checkerframework **Name:** checker-qual **Version:** 2.9.0 + * **POM Project URL:** [https://checkerframework.org](https://checkerframework.org) + * **POM License: The MIT License** - [http://opensource.org/licenses/MIT](http://opensource.org/licenses/MIT) + +1. **Group:** org.codehaus.jackson **Name:** jackson-core-asl **Version:** 1.9.11 + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM Project URL:** [http://jackson.codehaus.org](http://jackson.codehaus.org) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.codehaus.mojo **Name:** animal-sniffer-annotations **Version:** 1.18 + * **POM License: MIT license** - [http://www.opensource.org/licenses/mit-license.php](http://www.opensource.org/licenses/mit-license.php) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.junit.jupiter **Name:** junit-jupiter-api **Version:** 5.5.1 + * **POM Project URL:** [https://junit.org/junit5/](https://junit.org/junit5/) + * **POM License: Eclipse Public License v2.0** - [https://www.eclipse.org/legal/epl-v20.html](https://www.eclipse.org/legal/epl-v20.html) + +1. **Group:** org.junit.jupiter **Name:** junit-jupiter-params **Version:** 5.5.1 + * **POM Project URL:** [https://junit.org/junit5/](https://junit.org/junit5/) + * **POM License: Eclipse Public License v2.0** - [https://www.eclipse.org/legal/epl-v20.html](https://www.eclipse.org/legal/epl-v20.html) + +1. **Group:** org.junit.platform **Name:** junit-platform-commons **Version:** 1.5.1 + * **POM Project URL:** [https://junit.org/junit5/](https://junit.org/junit5/) + * **POM License: Eclipse Public License v2.0** - [https://www.eclipse.org/legal/epl-v20.html](https://www.eclipse.org/legal/epl-v20.html) + +1. **Group:** org.opentest4j **Name:** opentest4j **Version:** 1.2.0 + * **Manifest License:** The Apache License, Version 2.0 (Not packaged) + * **POM Project URL:** [https://github.com/ota4j-team/opentest4j](https://github.com/ota4j-team/opentest4j) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.threeten **Name:** threetenbp **Version:** 1.3.3 + * **Manifest Project URL:** [http://www.threeten.org](http://www.threeten.org) + * **Manifest license URL:** [https://raw.githubusercontent.com/ThreeTen/threetenbp/master/LICENSE.txt](https://raw.githubusercontent.com/ThreeTen/threetenbp/master/LICENSE.txt) + * **POM Project URL:** [https://www.threeten.org/threetenbp](https://www.threeten.org/threetenbp) + * **POM License: BSD 3-clause** - [https://raw.githubusercontent.com/ThreeTen/threetenbp/master/LICENSE.txt](https://raw.githubusercontent.com/ThreeTen/threetenbp/master/LICENSE.txt) + +## Compile, tests and tooling +1. **Group:** aopalliance **Name:** aopalliance **Version:** 1.0 + * **POM Project URL:** [http://aopalliance.sourceforge.net](http://aopalliance.sourceforge.net) + * **POM License: Public Domain** + +1. **Group:** com.beust **Name:** jcommander **Version:** 1.72 + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0](http://www.apache.org/licenses/LICENSE-2.0) + * **POM Project URL:** [http://jcommander.org](http://jcommander.org) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0](http://www.apache.org/licenses/LICENSE-2.0) + +1. **Group:** com.fasterxml.jackson.core **Name:** jackson-core **Version:** 2.9.9 + * **Project URL:** [https://github.com/FasterXML/jackson-core](https://github.com/FasterXML/jackson-core) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.github.kevinstern **Name:** software-and-algorithms **Version:** 1.0 + * **POM Project URL:** [https://www.github.com/KevinStern/software-and-algorithms](https://www.github.com/KevinStern/software-and-algorithms) + * **POM License: MIT License** - [http://www.opensource.org/licenses/mit-license.php](http://www.opensource.org/licenses/mit-license.php) + +1. **Group:** com.github.stephenc.jcip **Name:** jcip-annotations **Version:** 1.0-1 + * **POM Project URL:** [http://stephenc.github.com/jcip-annotations](http://stephenc.github.com/jcip-annotations) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.android **Name:** annotations **Version:** 4.1.1.4 + * **POM Project URL:** [http://source.android.com/](http://source.android.com/) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0](http://www.apache.org/licenses/LICENSE-2.0) + +1. **Group:** com.google.api **Name:** api-common **Version:** 1.8.1 + * **POM Project URL:** [https://github.com/googleapis/api-common-java](https://github.com/googleapis/api-common-java) + * **POM License: BSD** - [https://github.com/googleapis/api-common-java/blob/master/LICENSE](https://github.com/googleapis/api-common-java/blob/master/LICENSE) + +1. **Group:** com.google.api **Name:** gax **Version:** 1.48.1 + * **POM Project URL:** [https://github.com/googleapis/gax-java](https://github.com/googleapis/gax-java) + * **POM License: BSD** - [https://github.com/googleapis/gax-java/blob/master/LICENSE](https://github.com/googleapis/gax-java/blob/master/LICENSE) + +1. **Group:** com.google.api **Name:** gax-httpjson **Version:** 0.65.1 + * **POM Project URL:** [https://github.com/googleapis/gax-java](https://github.com/googleapis/gax-java) + * **POM License: BSD** - [https://github.com/googleapis/gax-java/blob/master/LICENSE](https://github.com/googleapis/gax-java/blob/master/LICENSE) + +1. **Group:** com.google.api-client **Name:** google-api-client **Version:** 1.30.2 + * **Manifest Project URL:** [https://developers.google.com/api-client-library/java/](https://developers.google.com/api-client-library/java/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.api.grpc **Name:** proto-google-cloud-datastore-v1 **Version:** 0.74.0 + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.api.grpc **Name:** proto-google-common-protos **Version:** 1.16.0 + * **POM Project URL:** [https://github.com/googleapis/common-protos-java](https://github.com/googleapis/common-protos-java) + * **POM License: Apache** - [https://github.com/googleapis/common-protos-java/blob/master/LICENSE](https://github.com/googleapis/common-protos-java/blob/master/LICENSE) + +1. **Group:** com.google.api.grpc **Name:** proto-google-iam-v1 **Version:** 0.12.0 + * **POM Project URL:** [https://github.com/googleapis/api-client-staging](https://github.com/googleapis/api-client-staging) + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.auth **Name:** google-auth-library-credentials **Version:** 0.17.1 + * **POM License: BSD New license** - [http://opensource.org/licenses/BSD-3-Clause](http://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.google.auth **Name:** google-auth-library-oauth2-http **Version:** 0.17.1 + * **POM License: BSD New license** - [http://opensource.org/licenses/BSD-3-Clause](http://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.google.auto **Name:** auto-common **Version:** 0.10 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.auto.value **Name:** auto-value-annotations **Version:** 1.6.6 + * **POM Project URL:** [https://github.com/google/auto/tree/master/value](https://github.com/google/auto/tree/master/value) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.cloud **Name:** google-cloud-core **Version:** 1.90.0 + * **POM Project URL:** [https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-core](https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-core) + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.cloud **Name:** google-cloud-core-http **Version:** 1.90.0 + * **POM Project URL:** [https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-core-http](https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-core-http) + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.cloud **Name:** google-cloud-datastore **Version:** 1.91.0 + * **POM Project URL:** [https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-datastore](https://github.com/googleapis/google-cloud-java/tree/master/google-cloud-clients/google-cloud-datastore) + * **POM License: Apache-2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.cloud.datastore **Name:** datastore-v1-proto-client **Version:** 1.6.0 + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.code.findbugs **Name:** jFormatString **Version:** 3.0.0 + * **POM Project URL:** [http://findbugs.sourceforge.net/](http://findbugs.sourceforge.net/) + * **POM License: GNU Lesser Public License** - [http://www.gnu.org/licenses/lgpl.html](http://www.gnu.org/licenses/lgpl.html) + +1. **Group:** com.google.code.findbugs **Name:** jsr305 **Version:** 3.0.2 + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM Project URL:** [http://findbugs.sourceforge.net/](http://findbugs.sourceforge.net/) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.code.gson **Name:** gson **Version:** 2.7 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.code.gson **Name:** gson **Version:** 2.8.5 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.errorprone **Name:** error_prone_annotation **Version:** 2.3.3 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.errorprone **Name:** error_prone_annotations **Version:** 2.3.3 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.errorprone **Name:** error_prone_check_api **Version:** 2.3.3 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.errorprone **Name:** error_prone_core **Version:** 2.3.3 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.errorprone **Name:** error_prone_type_annotations **Version:** 2.3.3 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.errorprone **Name:** javac **Version:** 9+181-r4173-1 + * **POM Project URL:** [https://github.com/google/error-prone-javac](https://github.com/google/error-prone-javac) + * **POM License: GNU General Public License, version 2, with the Classpath Exception** - [http://openjdk.java.net/legal/gplv2+ce.html](http://openjdk.java.net/legal/gplv2+ce.html) + +1. **Group:** com.google.flogger **Name:** flogger **Version:** 0.4 + * **POM Project URL:** [https://github.com/google/flogger](https://github.com/google/flogger) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.flogger **Name:** flogger-system-backend **Version:** 0.4 + * **POM Project URL:** [https://github.com/google/flogger](https://github.com/google/flogger) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.gradle **Name:** osdetector-gradle-plugin **Version:** 1.4.0 + * **POM Project URL:** [https://github.com/google/osdetector-gradle-plugin](https://github.com/google/osdetector-gradle-plugin) + * **POM License: Apache License 2.0** - [http://opensource.org/licenses/Apache-2.0](http://opensource.org/licenses/Apache-2.0) + +1. **Group:** com.google.guava **Name:** failureaccess **Version:** 1.0.1 + * **Manifest Project URL:** [https://github.com/google/guava/](https://github.com/google/guava/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.guava **Name:** guava **Version:** 28.1-jre + * **Manifest Project URL:** [https://github.com/google/guava/](https://github.com/google/guava/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.guava **Name:** guava-testlib **Version:** 28.1-jre + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.guava **Name:** listenablefuture **Version:** 9999.0-empty-to-avoid-conflict-with-guava + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client **Version:** 1.31.0 + * **Manifest Project URL:** [http://www.google.com/](http://www.google.com/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client-appengine **Version:** 1.31.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client-jackson **Version:** 1.20.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client-jackson2 **Version:** 1.31.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.http-client **Name:** google-http-client-protobuf **Version:** 1.20.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.j2objc **Name:** j2objc-annotations **Version:** 1.3 + * **POM Project URL:** [https://github.com/google/j2objc/](https://github.com/google/j2objc/) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.oauth-client **Name:** google-oauth-client **Version:** 1.30.1 + * **Manifest Project URL:** [http://www.google.com/](http://www.google.com/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.protobuf **Name:** protobuf-gradle-plugin **Version:** 0.8.8 + * **POM Project URL:** [https://github.com/google/protobuf-gradle-plugin](https://github.com/google/protobuf-gradle-plugin) + * **POM License: BSD 3-Clause** - [http://opensource.org/licenses/BSD-3-Clause](http://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.google.protobuf **Name:** protobuf-java **Version:** 3.4.0 + * **Manifest Project URL:** [https://developers.google.com/protocol-buffers/](https://developers.google.com/protocol-buffers/) + * **Manifest license URL:** [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + * **POM License: 3-Clause BSD License** - [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.protobuf **Name:** protobuf-java **Version:** 3.9.0 + * **Manifest Project URL:** [https://developers.google.com/protocol-buffers/](https://developers.google.com/protocol-buffers/) + * **Manifest license URL:** [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + * **POM License: 3-Clause BSD License** - [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.google.protobuf **Name:** protobuf-java-util **Version:** 3.9.0 + * **Manifest Project URL:** [https://developers.google.com/protocol-buffers/](https://developers.google.com/protocol-buffers/) + * **Manifest license URL:** [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + * **POM License: 3-Clause BSD License** - [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + +1. **Group:** com.google.protobuf **Name:** protoc **Version:** 3.9.0 + * **POM Project URL:** [https://developers.google.com/protocol-buffers/](https://developers.google.com/protocol-buffers/) + * **POM License: 3-Clause BSD License** - [https://opensource.org/licenses/BSD-3-Clause](https://opensource.org/licenses/BSD-3-Clause) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.truth **Name:** truth **Version:** 1.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.truth.extensions **Name:** truth-java8-extension **Version:** 1.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.truth.extensions **Name:** truth-liteproto-extension **Version:** 1.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.google.truth.extensions **Name:** truth-proto-extension **Version:** 1.0 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.googlecode.java-diff-utils **Name:** diffutils **Version:** 1.3.0 + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM Project URL:** [http://code.google.com/p/java-diff-utils/](http://code.google.com/p/java-diff-utils/) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.squareup **Name:** javapoet **Version:** 1.11.0 + * **POM Project URL:** [http://github.com/square/javapoet/](http://github.com/square/javapoet/) + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.squareup.okhttp **Name:** okhttp **Version:** 2.5.0 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** com.squareup.okio **Name:** okio **Version:** 1.13.0 + * **POM License: Apache 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** commons-codec **Name:** commons-codec **Version:** 1.11 + * **Project URL:** [http://commons.apache.org/proper/commons-codec/](http://commons.apache.org/proper/commons-codec/) + * **Manifest license URL:** [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: Apache License, Version 2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** commons-io **Name:** commons-io **Version:** 2.6 + * **Project URL:** [http://commons.apache.org/proper/commons-io/](http://commons.apache.org/proper/commons-io/) + * **Manifest license URL:** [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: Apache License, Version 2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** commons-lang **Name:** commons-lang **Version:** 2.6 + * **Project URL:** [http://commons.apache.org/lang/](http://commons.apache.org/lang/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** commons-logging **Name:** commons-logging **Version:** 1.2 + * **Project URL:** [http://commons.apache.org/proper/commons-logging/](http://commons.apache.org/proper/commons-logging/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** io.grpc **Name:** grpc-api **Version:** 1.23.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-context **Version:** 1.23.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-core **Version:** 1.23.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-okhttp **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-protobuf **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-protobuf-lite **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** grpc-stub **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.grpc **Name:** protoc-gen-grpc-java **Version:** 1.22.0 + * **POM Project URL:** [https://github.com/grpc/grpc-java](https://github.com/grpc/grpc-java) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** io.opencensus **Name:** opencensus-api **Version:** 0.23.0 + * **POM Project URL:** [https://github.com/census-instrumentation/opencensus-java](https://github.com/census-instrumentation/opencensus-java) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** io.opencensus **Name:** opencensus-contrib-grpc-metrics **Version:** 0.21.0 + * **POM Project URL:** [https://github.com/census-instrumentation/opencensus-java](https://github.com/census-instrumentation/opencensus-java) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** io.opencensus **Name:** opencensus-contrib-http-util **Version:** 0.21.0 + * **POM Project URL:** [https://github.com/census-instrumentation/opencensus-java](https://github.com/census-instrumentation/opencensus-java) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** io.perfmark **Name:** perfmark-api **Version:** 0.17.0 + * **POM Project URL:** [https://github.com/perfmark/perfmark](https://github.com/perfmark/perfmark) + * **POM License: Apache 2.0** - [https://opensource.org/licenses/Apache-2.0](https://opensource.org/licenses/Apache-2.0) + +1. **Group:** javax.annotation **Name:** javax.annotation-api **Version:** 1.3.2 + * **Manifest Project URL:** [https://javaee.github.io/glassfish](https://javaee.github.io/glassfish) + * **Manifest license URL:** [https://github.com/javaee/javax.annotation/blob/master/LICENSE](https://github.com/javaee/javax.annotation/blob/master/LICENSE) + * **POM Project URL:** [http://jcp.org/en/jsr/detail?id=250](http://jcp.org/en/jsr/detail?id=250) + * **POM License: CDDL + GPLv2 with classpath exception** - [https://github.com/javaee/javax.annotation/blob/master/LICENSE](https://github.com/javaee/javax.annotation/blob/master/LICENSE) + +1. **Group:** javax.annotation **Name:** jsr250-api **Version:** 1.0 + * **POM Project URL:** [http://jcp.org/aboutJava/communityprocess/final/jsr250/index.html](http://jcp.org/aboutJava/communityprocess/final/jsr250/index.html) + * **POM License: COMMON DEVELOPMENT AND DISTRIBUTION LICENSE (CDDL) Version 1.0** - [https://glassfish.dev.java.net/public/CDDLv1.0.html](https://glassfish.dev.java.net/public/CDDLv1.0.html) + +1. **Group:** javax.enterprise **Name:** cdi-api **Version:** 1.0 + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0](http://www.apache.org/licenses/LICENSE-2.0) + +1. **Group:** javax.inject **Name:** javax.inject **Version:** 1 + * **POM Project URL:** [http://code.google.com/p/atinject/](http://code.google.com/p/atinject/) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** junit **Name:** junit **Version:** 4.12 + * **POM Project URL:** [http://junit.org](http://junit.org) + * **POM License: Eclipse Public License 1.0** - [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + +1. **Group:** kr.motd.maven **Name:** os-maven-plugin **Version:** 1.4.0.Final + * **POM Project URL:** [https://github.com/trustin/os-maven-plugin/](https://github.com/trustin/os-maven-plugin/) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0](http://www.apache.org/licenses/LICENSE-2.0) + +1. **Group:** net.java.dev.javacc **Name:** javacc **Version:** 5.0 + * **POM Project URL:** [https://javacc.dev.java.net/](https://javacc.dev.java.net/) + * **POM License: Berkeley Software Distribution (BSD) License** - [http://www.opensource.org/licenses/bsd-license.html](http://www.opensource.org/licenses/bsd-license.html) + +1. **Group:** net.sourceforge.pmd **Name:** pmd-core **Version:** 6.16.0 + * **POM License: BSD-style** - [http://pmd.sourceforge.net/license.html](http://pmd.sourceforge.net/license.html) + +1. **Group:** net.sourceforge.pmd **Name:** pmd-java **Version:** 6.16.0 + * **POM License: BSD-style** - [http://pmd.sourceforge.net/license.html](http://pmd.sourceforge.net/license.html) + +1. **Group:** net.sourceforge.saxon **Name:** saxon **Version:** 9.1.0.8 + * **POM Project URL:** [http://saxon.sourceforge.net/](http://saxon.sourceforge.net/) + * **POM License: Mozilla Public License Version 1.0** - [http://www.mozilla.org/MPL/MPL-1.0.txt](http://www.mozilla.org/MPL/MPL-1.0.txt) + +1. **Group:** org.antlr **Name:** antlr4-runtime **Version:** 4.7 + * **Manifest Project URL:** [http://www.antlr.org](http://www.antlr.org) + * **Manifest license URL:** [http://www.antlr.org/license.html](http://www.antlr.org/license.html) + * **POM License: The BSD License** - [http://www.antlr.org/license.html](http://www.antlr.org/license.html) + +1. **Group:** org.apache.commons **Name:** commons-lang3 **Version:** 3.8.1 + * **Project URL:** [http://commons.apache.org/proper/commons-lang/](http://commons.apache.org/proper/commons-lang/) + * **Manifest license URL:** [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: Apache License, Version 2.0** - [https://www.apache.org/licenses/LICENSE-2.0.txt](https://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.apache.httpcomponents **Name:** httpclient **Version:** 4.5.9 + * **POM Project URL:** [http://hc.apache.org/httpcomponents-client](http://hc.apache.org/httpcomponents-client) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.apache.httpcomponents **Name:** httpcore **Version:** 4.4.11 + * **POM Project URL:** [http://hc.apache.org/httpcomponents-core-ga](http://hc.apache.org/httpcomponents-core-ga) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.apache.maven **Name:** maven-artifact **Version:** 3.2.1 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.apache.maven **Name:** maven-model **Version:** 3.2.1 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.apache.maven **Name:** maven-plugin-api **Version:** 3.2.1 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.apiguardian **Name:** apiguardian-api **Version:** 1.1.0 + * **POM Project URL:** [https://github.com/apiguardian-team/apiguardian](https://github.com/apiguardian-team/apiguardian) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.checkerframework **Name:** checker-compat-qual **Version:** 2.5.5 + * **POM Project URL:** [https://checkerframework.org](https://checkerframework.org) + * **POM License: GNU General Public License, version 2 (GPL2), with the classpath exception** - [http://www.gnu.org/software/classpath/license.html](http://www.gnu.org/software/classpath/license.html) + * **POM License: The MIT License** - [http://opensource.org/licenses/MIT](http://opensource.org/licenses/MIT) + +1. **Group:** org.checkerframework **Name:** checker-qual **Version:** 2.8.1 + * **POM Project URL:** [https://checkerframework.org](https://checkerframework.org) + * **POM License: The MIT License** - [http://opensource.org/licenses/MIT](http://opensource.org/licenses/MIT) + +1. **Group:** org.checkerframework **Name:** checker-qual **Version:** 2.9.0 + * **POM Project URL:** [https://checkerframework.org](https://checkerframework.org) + * **POM License: The MIT License** - [http://opensource.org/licenses/MIT](http://opensource.org/licenses/MIT) + +1. **Group:** org.checkerframework **Name:** dataflow **Version:** 2.5.3 + * **POM Project URL:** [https://checkerframework.org](https://checkerframework.org) + * **POM License: GNU General Public License, version 2 (GPL2), with the classpath exception** - [http://www.gnu.org/software/classpath/license.html](http://www.gnu.org/software/classpath/license.html) + * **POM License: The MIT License** - [http://opensource.org/licenses/MIT](http://opensource.org/licenses/MIT) + +1. **Group:** org.checkerframework **Name:** javacutil **Version:** 2.5.3 + * **POM Project URL:** [https://checkerframework.org](https://checkerframework.org) + * **POM License: GNU General Public License, version 2 (GPL2), with the classpath exception** - [http://www.gnu.org/software/classpath/license.html](http://www.gnu.org/software/classpath/license.html) + * **POM License: The MIT License** - [http://opensource.org/licenses/MIT](http://opensource.org/licenses/MIT) + +1. **Group:** org.codehaus.jackson **Name:** jackson-core-asl **Version:** 1.9.11 + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM Project URL:** [http://jackson.codehaus.org](http://jackson.codehaus.org) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.codehaus.mojo **Name:** animal-sniffer-annotations **Version:** 1.18 + * **POM License: MIT license** - [http://www.opensource.org/licenses/mit-license.php](http://www.opensource.org/licenses/mit-license.php) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.codehaus.plexus **Name:** plexus-classworlds **Version:** 2.4 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.codehaus.plexus **Name:** plexus-component-annotations **Version:** 1.5.5 + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.codehaus.plexus **Name:** plexus-utils **Version:** 3.0.17 + * **POM Project URL:** [http://plexus.codehaus.org/plexus-utils](http://plexus.codehaus.org/plexus-utils) + * **POM License: Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0](http://www.apache.org/licenses/LICENSE-2.0) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.eclipse.sisu **Name:** org.eclipse.sisu.inject **Version:** 0.0.0.M5 + * **Manifest Project URL:** [http://www.eclipse.org/sisu/](http://www.eclipse.org/sisu/) + * **Manifest license URL:** [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + * **POM License: Eclipse Public License, Version 1.0** - [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + +1. **Group:** org.eclipse.sisu **Name:** org.eclipse.sisu.plexus **Version:** 0.0.0.M5 + * **Manifest Project URL:** [http://www.eclipse.org/sisu/](http://www.eclipse.org/sisu/) + * **Manifest license URL:** [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + * **POM License: Eclipse Public License, Version 1.0** - [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + +1. **Group:** org.hamcrest **Name:** hamcrest-all **Version:** 1.3 + * **POM License: New BSD License** - [http://www.opensource.org/licenses/bsd-license.php](http://www.opensource.org/licenses/bsd-license.php) + +1. **Group:** org.hamcrest **Name:** hamcrest-core **Version:** 1.3 + * **POM License: New BSD License** - [http://www.opensource.org/licenses/bsd-license.php](http://www.opensource.org/licenses/bsd-license.php) + +1. **Group:** org.jacoco **Name:** org.jacoco.agent **Version:** 0.8.4 + * **Manifest license URL:** [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + * **POM License: Eclipse Public License v1.0** - [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + +1. **Group:** org.jacoco **Name:** org.jacoco.ant **Version:** 0.8.4 + * **Manifest license URL:** [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + * **POM License: Eclipse Public License v1.0** - [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + +1. **Group:** org.jacoco **Name:** org.jacoco.core **Version:** 0.8.4 + * **Manifest license URL:** [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + * **POM License: Eclipse Public License v1.0** - [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + +1. **Group:** org.jacoco **Name:** org.jacoco.report **Version:** 0.8.4 + * **Manifest license URL:** [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + * **POM License: Eclipse Public License v1.0** - [http://www.eclipse.org/legal/epl-v10.html](http://www.eclipse.org/legal/epl-v10.html) + +1. **Group:** org.junit.jupiter **Name:** junit-jupiter-api **Version:** 5.5.1 + * **POM Project URL:** [https://junit.org/junit5/](https://junit.org/junit5/) + * **POM License: Eclipse Public License v2.0** - [https://www.eclipse.org/legal/epl-v20.html](https://www.eclipse.org/legal/epl-v20.html) + +1. **Group:** org.junit.jupiter **Name:** junit-jupiter-engine **Version:** 5.5.1 + * **POM Project URL:** [https://junit.org/junit5/](https://junit.org/junit5/) + * **POM License: Eclipse Public License v2.0** - [https://www.eclipse.org/legal/epl-v20.html](https://www.eclipse.org/legal/epl-v20.html) + +1. **Group:** org.junit.jupiter **Name:** junit-jupiter-params **Version:** 5.5.1 + * **POM Project URL:** [https://junit.org/junit5/](https://junit.org/junit5/) + * **POM License: Eclipse Public License v2.0** - [https://www.eclipse.org/legal/epl-v20.html](https://www.eclipse.org/legal/epl-v20.html) + +1. **Group:** org.junit.platform **Name:** junit-platform-commons **Version:** 1.5.1 + * **POM Project URL:** [https://junit.org/junit5/](https://junit.org/junit5/) + * **POM License: Eclipse Public License v2.0** - [https://www.eclipse.org/legal/epl-v20.html](https://www.eclipse.org/legal/epl-v20.html) + +1. **Group:** org.junit.platform **Name:** junit-platform-engine **Version:** 1.5.1 + * **POM Project URL:** [https://junit.org/junit5/](https://junit.org/junit5/) + * **POM License: Eclipse Public License v2.0** - [https://www.eclipse.org/legal/epl-v20.html](https://www.eclipse.org/legal/epl-v20.html) + +1. **Group:** org.opentest4j **Name:** opentest4j **Version:** 1.2.0 + * **Manifest License:** The Apache License, Version 2.0 (Not packaged) + * **POM Project URL:** [https://github.com/ota4j-team/opentest4j](https://github.com/ota4j-team/opentest4j) + * **POM License: The Apache License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.ow2.asm **Name:** asm **Version:** 7.1 + * **Manifest Project URL:** [http://asm.ow2.org](http://asm.ow2.org) + * **POM Project URL:** [http://asm.ow2.org/](http://asm.ow2.org/) + * **POM License: BSD** - [http://asm.ow2.org/license.html](http://asm.ow2.org/license.html) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.ow2.asm **Name:** asm-analysis **Version:** 7.1 + * **Manifest Project URL:** [http://asm.ow2.org](http://asm.ow2.org) + * **POM Project URL:** [http://asm.ow2.org/](http://asm.ow2.org/) + * **POM License: BSD** - [http://asm.ow2.org/license.html](http://asm.ow2.org/license.html) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.ow2.asm **Name:** asm-commons **Version:** 7.1 + * **Manifest Project URL:** [http://asm.ow2.org](http://asm.ow2.org) + * **POM Project URL:** [http://asm.ow2.org/](http://asm.ow2.org/) + * **POM License: BSD** - [http://asm.ow2.org/license.html](http://asm.ow2.org/license.html) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.ow2.asm **Name:** asm-tree **Version:** 7.1 + * **Manifest Project URL:** [http://asm.ow2.org](http://asm.ow2.org) + * **POM Project URL:** [http://asm.ow2.org/](http://asm.ow2.org/) + * **POM License: BSD** - [http://asm.ow2.org/license.html](http://asm.ow2.org/license.html) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.pcollections **Name:** pcollections **Version:** 2.1.2 + * **POM Project URL:** [http://pcollections.org](http://pcollections.org) + * **POM License: The MIT License** - [http://www.opensource.org/licenses/mit-license.php](http://www.opensource.org/licenses/mit-license.php) + +1. **Group:** org.sonatype.sisu **Name:** sisu-guice **Version:** 3.1.0 + * **Manifest Project URL:** [http://code.google.com/p/google-guice/](http://code.google.com/p/google-guice/) + * **Manifest license URL:** [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + * **POM License: The Apache Software License, Version 2.0** - [http://www.apache.org/licenses/LICENSE-2.0.txt](http://www.apache.org/licenses/LICENSE-2.0.txt) + +1. **Group:** org.threeten **Name:** threetenbp **Version:** 1.3.3 + * **Manifest Project URL:** [http://www.threeten.org](http://www.threeten.org) + * **Manifest license URL:** [https://raw.githubusercontent.com/ThreeTen/threetenbp/master/LICENSE.txt](https://raw.githubusercontent.com/ThreeTen/threetenbp/master/LICENSE.txt) + * **POM Project URL:** [https://www.threeten.org/threetenbp](https://www.threeten.org/threetenbp) + * **POM License: BSD 3-clause** - [https://raw.githubusercontent.com/ThreeTen/threetenbp/master/LICENSE.txt](https://raw.githubusercontent.com/ThreeTen/threetenbp/master/LICENSE.txt) + + + + The dependencies distributed under several licenses, are used according their commercial-use-friendly license. + + +This report was generated on **Mon Sep 30 20:28:37 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file diff --git a/testutil-gcloud/build.gradle b/testutil-gcloud/build.gradle index 1e1ac6425..a4e28bf13 100644 --- a/testutil-gcloud/build.gradle +++ b/testutil-gcloud/build.gradle @@ -19,4 +19,6 @@ */ dependencies { + implementation project(path: ':datastore') + implementation deps.test.junit5Api } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/BigDataTester.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/BigDataTester.java similarity index 92% rename from datastore/src/test/java/io/spine/server/storage/datastore/BigDataTester.java rename to testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/BigDataTester.java index dea0e4fa4..244d34fb6 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/BigDataTester.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/BigDataTester.java @@ -18,7 +18,7 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.server.storage.datastore; +package io.spine.testing.server.storage.datastore; import com.google.common.base.Throwables; import io.spine.client.ResponseFormat; @@ -55,7 +55,7 @@ * @param * the type of the ID in the tested {@linkplain RecordStorage} */ -public class BigDataTester implements Logging { +public final class BigDataTester implements Logging { private static final int DEFAULT_BULK_SIZE = 500; @@ -80,13 +80,14 @@ public static Builder newBuilder() { * *

The execution flow is as follows: *

    - *
  1. 1. Produce the records with the given {@link EntryFactory} - *
  2. 2. Measure the time of the {@linkplain RecordStorage#write(Map) bulk write} - *
  3. 3. Fail if the time is over the specified limit - *
  4. 4. Wait 1 second to ensure the Datastore has established the data consistency - *
  5. 5. Measure the time of the {@linkplain RecordStorage#readAll() bulk read} - *
  6. 6. Fail if the time is over the specified limit - *
  7. 7. Check the count of the records written and read is equal + *
  8. Produce the records with the given {@link EntryFactory}. + *
  9. Measure the time of the {@linkplain RecordStorage#write(Map) bulk write}. + *
  10. Fail if the time is over the specified limit. + *
  11. Wait 1 second to ensure the Datastore has established the data consistency. + *
  12. Measure the time of the + * {@linkplain RecordStorage#readAll(ResponseFormat) bulk read}. + *
  13. Fail if the time is over the specified limit. + *
  14. Check the count of the records written and read is equal. *
* *

This method performs {@code debug} logging of the measure results. To see the log, run diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/given/CountingDatastoreWrapper.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/CountingDatastoreWrapper.java similarity index 96% rename from datastore/src/test/java/io/spine/server/storage/datastore/given/CountingDatastoreWrapper.java rename to testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/CountingDatastoreWrapper.java index 9700b85fe..f3b436caf 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/given/CountingDatastoreWrapper.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/CountingDatastoreWrapper.java @@ -18,14 +18,13 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.server.storage.datastore.given; +package io.spine.testing.server.storage.datastore; import com.google.cloud.datastore.Datastore; import com.google.cloud.datastore.Entity; import com.google.cloud.datastore.Key; import com.google.cloud.datastore.StructuredQuery; import io.spine.server.storage.datastore.DsQueryIterator; -import io.spine.server.storage.datastore.TestDatastoreWrapper; import org.checkerframework.checker.nullness.qual.Nullable; import java.util.Collection; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/SpyStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java similarity index 78% rename from datastore/src/test/java/io/spine/server/storage/datastore/SpyStorageFactory.java rename to testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java index 3a5fed069..e5167dedc 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/SpyStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java @@ -18,29 +18,25 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.server.storage.datastore; +package io.spine.testing.server.storage.datastore; -import io.spine.annotation.Internal; +import io.spine.server.storage.datastore.DatastoreWrapper; /** * A {@link TestDatastoreStorageFactory} which allows to inject a custom {@link DatastoreWrapper}. - * - *

This class is not moved to the test environment because it uses the package-private method of - * {@link DatastoreWrapper}. */ -final class SpyStorageFactory extends TestDatastoreStorageFactory { +public final class SpyStorageFactory extends TestDatastoreStorageFactory { private static DatastoreWrapper injectedWrapper = null; - static void injectWrapper(DatastoreWrapper wrapper) { + public static void injectWrapper(DatastoreWrapper wrapper) { injectedWrapper = wrapper; } - SpyStorageFactory() { + public SpyStorageFactory() { super(injectedWrapper.datastore()); } - @Internal @Override protected DatastoreWrapper createDatastoreWrapper(boolean multitenant) { return injectedWrapper; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/TestDatastoreStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java similarity index 94% rename from datastore/src/test/java/io/spine/server/storage/datastore/TestDatastoreStorageFactory.java rename to testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java index 7aab653cc..11f91cc0b 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/TestDatastoreStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java @@ -18,13 +18,14 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.server.storage.datastore; +package io.spine.testing.server.storage.datastore; import com.google.cloud.datastore.Datastore; import com.google.cloud.datastore.DatastoreOptions; import com.google.common.flogger.FluentLogger; import io.spine.annotation.Internal; -import io.spine.server.storage.datastore.given.TestDatastores; +import io.spine.server.storage.datastore.DatastoreStorageFactory; +import io.spine.server.storage.datastore.DatastoreWrapper; import io.spine.server.storage.datastore.type.DatastoreTypeRegistryFactory; import org.checkerframework.checker.nullness.qual.MonotonicNonNull; @@ -79,11 +80,10 @@ protected DatastoreWrapper createDatastoreWrapper(boolean multitenant) { /** * Performs operations on setting up the local datastore. * - *

General usage is testing. *

By default is a NoOp, but can be overridden. */ - @SuppressWarnings("EmptyMethod") public void setUp() { + // NO-OP. See doc. } /** @@ -100,7 +100,7 @@ public void tearDown() { } /** - * Clears all data in the local Datastore. + * Clears all data in the Datastore. * * @see #tearDown() */ diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/TestDatastoreWrapper.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java similarity index 90% rename from datastore/src/test/java/io/spine/server/storage/datastore/TestDatastoreWrapper.java rename to testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java index 48e8f09f4..91d28934d 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/TestDatastoreWrapper.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java @@ -18,7 +18,7 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.server.storage.datastore; +package io.spine.testing.server.storage.datastore; import com.google.cloud.datastore.Datastore; import com.google.cloud.datastore.DatastoreException; @@ -26,13 +26,15 @@ import com.google.cloud.datastore.KeyFactory; import com.google.cloud.datastore.Query; import com.google.cloud.datastore.StructuredQuery; -import io.spine.server.storage.datastore.tenant.TestNamespaceSuppliers; +import io.spine.server.storage.datastore.DatastoreWrapper; +import io.spine.server.storage.datastore.Kind; import java.util.ArrayList; import java.util.Collection; import java.util.List; import static com.google.common.collect.Lists.newArrayList; +import static io.spine.util.Exceptions.newIllegalStateException; /** * Custom extension of the {@link DatastoreWrapper} for the integration testing. @@ -93,7 +95,7 @@ public void update(Entity entity) throws DatastoreException { } @Override - void dropTable(String table) { + protected void dropTable(String table) { if (!waitForConsistency) { super.dropTable(table); } else { @@ -115,7 +117,7 @@ private void dropTableConsistently(String table) { try { Thread.sleep(CONSISTENCY_AWAIT_TIME_MS); } catch (InterruptedException e) { - throw new RuntimeException(e); + throw new IllegalStateException(e); } } @@ -132,9 +134,9 @@ private void dropTableConsistently(String table) { } if (cleanupAttempts >= MAX_CLEANUP_ATTEMPTS && remainingEntityCount > 0) { - throw new RuntimeException("Cannot cleanup the table: " + table + - ". Remaining entity count is " + - remainingEntityCount); + throw newIllegalStateException( + "Cannot cleanup the table: %s. Remaining entity count is %d", + table, remainingEntityCount); } } @@ -150,7 +152,7 @@ private void waitForConsistency() { try { Thread.sleep(CONSISTENCY_AWAIT_TIME_MS); } catch (InterruptedException e) { - throw new RuntimeException(e); + throw new IllegalStateException(e); } } } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/given/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java similarity index 97% rename from datastore/src/test/java/io/spine/server/storage/datastore/given/TestDatastores.java rename to testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index b43958d9a..8a0ce39d4 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/given/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -18,7 +18,7 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.server.storage.datastore.given; +package io.spine.testing.server.storage.datastore; import com.google.auth.oauth2.ServiceAccountCredentials; import com.google.cloud.NoCredentials; @@ -36,7 +36,7 @@ /** * Provides test {@link Datastore} instances. */ -public class TestDatastores { +public final class TestDatastores { private static final ProjectId TEST_PROJECT_ID = ProjectId.of("spine-dev"); @@ -112,6 +112,7 @@ private static final class Ci extends Options implements Logging { private static final DatastoreOptions INSTANCE = new Ci().create(); private Ci() { + super(); try { InputStream is = TestDatastores.class.getResourceAsStream(CREDENTIALS_FILE_PATH); BufferedInputStream bufferedStream = new BufferedInputStream(is); diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/given/TestEnvironment.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestEnvironment.java similarity index 97% rename from datastore/src/test/java/io/spine/server/storage/datastore/given/TestEnvironment.java rename to testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestEnvironment.java index 617934664..e17c2255c 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/given/TestEnvironment.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestEnvironment.java @@ -18,7 +18,7 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.server.storage.datastore.given; +package io.spine.testing.server.storage.datastore; import io.spine.server.ContextSpec; diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java new file mode 100644 index 000000000..86189b014 --- /dev/null +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java @@ -0,0 +1,38 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.testing.server.storage.datastore; + +import io.spine.server.storage.datastore.tenant.NamespaceSupplier; +import io.spine.server.storage.datastore.tenant.NsConverterFactory; + +final class TestNamespaceSuppliers { + + private TestNamespaceSuppliers() { + } + + static NamespaceSupplier singleTenant() { + return NamespaceSupplier.singleTenant(); + } + + static NamespaceSupplier multitenant() { + return NamespaceSupplier.multitenant(NsConverterFactory.defaults()); + } +} diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/package-info.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/package-info.java new file mode 100644 index 000000000..f6830d6d3 --- /dev/null +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/package-info.java @@ -0,0 +1,31 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/** + * This package contains the testing utils for the Google Cloud Datastore storage implementation. + */ + +@CheckReturnValue +@ParametersAreNonnullByDefault +package io.spine.testing.server.storage.datastore; + +import com.google.errorprone.annotations.CheckReturnValue; + +import javax.annotation.ParametersAreNonnullByDefault; From dced052c3cfc36d3ffc5427d0d74a69b27bf906d Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 14:26:29 +0300 Subject: [PATCH 03/30] Remove `BigDataTester` from `testutil-gcloud` --- .../java/io/spine}/server/storage/datastore/BigDataTester.java | 2 +- .../io/spine/server/storage/datastore/DsRecordStorageTest.java | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) rename {testutil-gcloud/src/main/java/io/spine/testing => datastore/src/test/java/io/spine}/server/storage/datastore/BigDataTester.java (99%) diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/BigDataTester.java b/datastore/src/test/java/io/spine/server/storage/datastore/BigDataTester.java similarity index 99% rename from testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/BigDataTester.java rename to datastore/src/test/java/io/spine/server/storage/datastore/BigDataTester.java index 244d34fb6..d63bf3f55 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/BigDataTester.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/BigDataTester.java @@ -18,7 +18,7 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.testing.server.storage.datastore; +package io.spine.server.storage.datastore; import com.google.common.base.Throwables; import io.spine.client.ResponseFormat; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java index 8042c9740..acb0b7cb5 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java @@ -53,7 +53,6 @@ import io.spine.test.storage.Project; import io.spine.test.storage.ProjectId; import io.spine.test.storage.Task; -import io.spine.testing.server.storage.datastore.BigDataTester; import io.spine.testing.server.storage.datastore.CountingDatastoreWrapper; import io.spine.testing.server.storage.datastore.SpyStorageFactory; import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; From 9494e73d1e29b2150e52faf7ed4de0d73be5bc89 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 14:49:42 +0300 Subject: [PATCH 04/30] Clean up the code --- .../io/spine/server/storage/datastore/DatastoreWrapper.java | 2 -- .../server/storage/datastore/TestDatastoreStorageFactory.java | 2 +- .../testing/server/storage/datastore/TestDatastoreWrapper.java | 2 +- .../spine/testing/server/storage/datastore/TestDatastores.java | 3 ++- 4 files changed, 4 insertions(+), 5 deletions(-) diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java index 4819f8ed5..b908ca35d 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java @@ -386,7 +386,6 @@ public void delete(Key... keys) { * @param table * kind (a.k.a. type, table, etc.) of the records to delete */ - @VisibleForTesting protected void dropTable(String table) { Namespace namespace = currentNamespace(); StructuredQuery query = @@ -399,7 +398,6 @@ protected void dropTable(String table) { deleteEntities(entities); } - @VisibleForTesting protected void deleteEntities(Collection entities) { List keyList = entities.stream() diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java index 11f91cc0b..a90df157e 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java @@ -80,7 +80,7 @@ protected DatastoreWrapper createDatastoreWrapper(boolean multitenant) { /** * Performs operations on setting up the local datastore. * - *

By default is a NoOp, but can be overridden. + *

By default is a NO-OP, but can be overridden. */ public void setUp() { // NO-OP. See doc. diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java index 91d28934d..fa5718f50 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java @@ -133,7 +133,7 @@ private void dropTableConsistently(String table) { } } - if (cleanupAttempts >= MAX_CLEANUP_ATTEMPTS && remainingEntityCount > 0) { + if (cleanupAttempts >= MAX_CLEANUP_ATTEMPTS) { throw newIllegalStateException( "Cannot cleanup the table: %s. Remaining entity count is %d", table, remainingEntityCount); diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index 8a0ce39d4..5847cab11 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -38,6 +38,7 @@ */ public final class TestDatastores { + @SuppressWarnings("DuplicateStringLiteralInspection") // Project name duplication. private static final ProjectId TEST_PROJECT_ID = ProjectId.of("spine-dev"); /** Prevent this test utility class from being instantiated. */ @@ -118,7 +119,7 @@ private Ci() { BufferedInputStream bufferedStream = new BufferedInputStream(is); ServiceAccountCredentials credentials = fromStream(bufferedStream); builder().setCredentials(credentials); - } catch (@SuppressWarnings("OverlyBroadCatchBlock") IOException e) { + } catch (IOException e) { _warn().log("Cannot find the credentials file `%s`.", CREDENTIALS_FILE_PATH); } } From 5eface1cb1a2ef0d09a4af92afdfba938b828f00 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 17:25:30 +0300 Subject: [PATCH 05/30] Make created datastore instances configurable, de-singletonize them Also the datastore emulator will now run on the default port 8081. --- .../DatastoreStorageFactoryBuilderTest.java | 4 +- .../DatastoreStorageFactoryTest.java | 4 +- ...AggregateStorageLifecycleHandlingTest.java | 4 +- .../datastore/DsAggregateStorageTest.java | 4 +- .../DsAggregateStorageTruncationTest.java | 2 +- .../storage/datastore/DsInboxStorageTest.java | 2 +- .../datastore/DsProjectionStorageTest.java | 4 +- .../datastore/DsPropertyStorageTest.java | 4 +- .../datastore/DsShardedWorkRegistryTest.java | 2 +- .../given/DatastoreWrapperTestEnv.java | 4 +- .../given/DsRecordStorageTestEnv.java | 2 +- .../datastore/tenant/NamespaceTest.java | 4 +- .../datastore/type/DsColumnTypesTest.java | 5 +- license-report.md | 6 +- scripts/start-datastore.bat | 2 +- scripts/start-datastore.sh | 2 +- .../TestDatastoreStorageFactory.java | 42 ++---- .../storage/datastore/TestDatastores.java | 124 +++++++----------- 18 files changed, 91 insertions(+), 130 deletions(-) diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java index c2103741d..8acb3bb6a 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java @@ -40,7 +40,7 @@ import static io.spine.testing.DisplayNames.HAVE_PARAMETERLESS_CTOR; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; import static io.spine.testing.Tests.assertHasPrivateParameterlessCtor; -import static io.spine.testing.server.storage.datastore.TestDatastores.projectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.testProjectId; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertThrows; @@ -102,7 +102,7 @@ class Namespaces { void setUp() { builder = DatastoreOptions .newBuilder() - .setProjectId(projectId().getValue()); + .setProjectId(testProjectId().getValue()); } @Test diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java index 4e11fcd9d..1e776821f 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java @@ -47,7 +47,7 @@ import static io.spine.server.tenant.TenantAwareRunner.with; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; import static io.spine.testing.server.storage.datastore.TestDatastores.local; -import static io.spine.testing.server.storage.datastore.TestDatastores.projectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.testProjectId; import static org.junit.jupiter.api.Assertions.assertNotEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertSame; @@ -177,7 +177,7 @@ private static Key.Builder whiteForTenant(DsPropertyStorage storage, TenantId te with(tenant).run( () -> storage.write(recordId, message) ); - return Key.newBuilder(projectId().getValue(), + return Key.newBuilder(testProjectId().getValue(), TypeName.of(message) .value(), recordId.getValue()); diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java index cac7e8125..41b639d8f 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java @@ -30,14 +30,14 @@ import org.junit.jupiter.api.BeforeAll; import org.junit.jupiter.api.DisplayName; -import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; +import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.local; import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; @DisplayName("`DsAggregateStorage` lifecycle handling should") class DsAggregateStorageLifecycleHandlingTest extends AggregateStorageLifecycleFlagsHandlingTest { - private static final TestDatastoreStorageFactory datastoreFactory = defaultInstance(); + private static final TestDatastoreStorageFactory datastoreFactory = local(); @BeforeAll static void setUpClass() { diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java index debc2d032..ce5a54c4a 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java @@ -71,7 +71,7 @@ import static io.spine.server.aggregate.given.Given.CommandMessage.addTask; import static io.spine.server.storage.datastore.DatastoreWrapper.MAX_ENTITIES_PER_WRITE_REQUEST; import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.datastoreFactory; -import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; +import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.local; import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; @@ -82,7 +82,7 @@ @DisplayName("`DsAggregateStorage` should") class DsAggregateStorageTest extends AggregateStorageTest { - private static final TestDatastoreStorageFactory datastoreFactory = defaultInstance(); + private static final TestDatastoreStorageFactory datastoreFactory = local(); @BeforeAll static void setUpClass() { diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTruncationTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTruncationTest.java index b249155b6..2cfec67e3 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTruncationTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTruncationTest.java @@ -30,6 +30,6 @@ public class DsAggregateStorageTruncationTest extends AggregateStorageTruncation @Override protected StorageFactory storageFactory() { - return TestDatastoreStorageFactory.defaultInstance(); + return TestDatastoreStorageFactory.local(); } } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsInboxStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsInboxStorageTest.java index c7c1a1935..45fc19e89 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsInboxStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsInboxStorageTest.java @@ -58,7 +58,7 @@ class DsInboxStorageTest extends InboxStorageTest { private final TestDatastoreStorageFactory factory = - TestDatastoreStorageFactory.defaultInstance(); + TestDatastoreStorageFactory.local(); @Override @BeforeEach diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java index afd8f0070..57b4f177e 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java @@ -36,13 +36,13 @@ import org.junit.jupiter.api.DisplayName; import static io.spine.base.Time.currentTime; -import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; +import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.local; import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; @DisplayName("`DsProjectionStorage` should") class DsProjectionStorageTest extends ProjectionStorageTest { - private static final TestDatastoreStorageFactory datastoreFactory = defaultInstance(); + private static final TestDatastoreStorageFactory datastoreFactory = local(); @Override protected Class getTestEntityClass() { diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java index 648bd6f7b..918ed5474 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java @@ -23,14 +23,14 @@ import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; -import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.defaultInstance; +import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.local; import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; import static org.junit.jupiter.api.Assertions.assertNotNull; @DisplayName("`DsPropertyStorage` should") class DsPropertyStorageTest { - private static final TestDatastoreStorageFactory datastoreFactory = defaultInstance(); + private static final TestDatastoreStorageFactory datastoreFactory = local(); @SuppressWarnings("DuplicateStringLiteralInspection") // OK for tests. @Test diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsShardedWorkRegistryTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsShardedWorkRegistryTest.java index 7a4afdfde..a500a020d 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsShardedWorkRegistryTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsShardedWorkRegistryTest.java @@ -52,7 +52,7 @@ class DsShardedWorkRegistryTest extends ShardedWorkRegistryTest { private static final NodeId nodeId = newNode(); private final TestDatastoreStorageFactory factory = - TestDatastoreStorageFactory.defaultInstance(); + TestDatastoreStorageFactory.local(); private DsShardedWorkRegistry registry; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java b/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java index 022c62a35..2f0a39790 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java @@ -40,6 +40,8 @@ public class DatastoreWrapperTestEnv { public static final String NAMESPACE_HOLDER_KIND = "spine.test.NAMESPACE_HOLDER_KIND"; public static final Kind GENERIC_ENTITY_KIND = Kind.of("my.entity"); + private static final String SERVICE_ACCOUNT_FILE_PATH = "spine-dev.json"; + /** * Prevents instantiation of this test environment. */ @@ -71,6 +73,6 @@ public static Datastore localDatastore() { } public static Datastore remoteDatastore() { - return TestDatastores.remote(); + return TestDatastores.remote(SERVICE_ACCOUNT_FILE_PATH); } } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/given/DsRecordStorageTestEnv.java b/datastore/src/test/java/io/spine/server/storage/datastore/given/DsRecordStorageTestEnv.java index f8d9ffade..0c6b0c6fd 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/given/DsRecordStorageTestEnv.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/given/DsRecordStorageTestEnv.java @@ -90,7 +90,7 @@ private DsRecordStorageTestEnv() { } public static TestDatastoreStorageFactory datastoreFactory() { - return TestDatastoreStorageFactory.defaultInstance(); + return TestDatastoreStorageFactory.local(); } public static OrderBy emptyOrderBy() { diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java index 5196417b4..7c1456d78 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java @@ -27,11 +27,11 @@ import io.spine.net.EmailAddress; import io.spine.net.InternetDomain; import io.spine.server.storage.datastore.ProjectId; -import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; +import static io.spine.testing.server.storage.datastore.TestDatastores.testProjectId; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; @@ -44,7 +44,7 @@ class NamespaceTest { @Test @DisplayName(NOT_ACCEPT_NULLS) void testNulls() { - ProjectId defaultProjectId = TestDatastores.projectId(); + ProjectId defaultProjectId = testProjectId(); Key defaultKey = Key.newBuilder(defaultProjectId.getValue(), "kind", "name") .build(); new NullPointerTester() diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java index fe3a441c4..57575bf84 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java @@ -30,7 +30,6 @@ import io.spine.json.Json; import io.spine.test.storage.Project; import io.spine.testdata.Sample; -import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; @@ -41,6 +40,7 @@ import static io.spine.server.storage.datastore.type.DsColumnTypes.timestampType; import static io.spine.testing.DisplayNames.HAVE_PARAMETERLESS_CTOR; import static io.spine.testing.Tests.assertHasPrivateParameterlessCtor; +import static io.spine.testing.server.storage.datastore.TestDatastores.testProjectId; @DisplayName("DsColumnTypes should") class DsColumnTypesTest { @@ -225,8 +225,7 @@ private void setDatastoreType(DatastoreColumnType type, } private static BaseEntity.Builder entityBuilder() { - String projectId = TestDatastores.projectId() - .value(); + String projectId = testProjectId().value(); Key key = Key.newBuilder(projectId, "some-entity-kind", "some-name") .build(); Entity.Builder builder = Entity.newBuilder(key); diff --git a/license-report.md b/license-report.md index 048e502de..d2eeb4f71 100644 --- a/license-report.md +++ b/license-report.md @@ -734,7 +734,7 @@ The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Mon Sep 30 20:28:12 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 17:20:30 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -1474,7 +1474,7 @@ This report was generated on **Mon Sep 30 20:28:12 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Mon Sep 30 20:28:25 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 17:20:43 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -2234,4 +2234,4 @@ This report was generated on **Mon Sep 30 20:28:25 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Mon Sep 30 20:28:37 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file +This report was generated on **Tue Oct 01 17:20:55 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file diff --git a/scripts/start-datastore.bat b/scripts/start-datastore.bat index 2d3890a00..9e8e9130e 100644 --- a/scripts/start-datastore.bat +++ b/scripts/start-datastore.bat @@ -1 +1 @@ -gcloud beta emulators datastore start --project=spine-dev --host-port=localhost:8080 --consistency 1.0 --no-store-on-disk +gcloud beta emulators datastore start --project=spine-dev --consistency 1.0 --no-store-on-disk diff --git a/scripts/start-datastore.sh b/scripts/start-datastore.sh index 2d3890a00..9e8e9130e 100755 --- a/scripts/start-datastore.sh +++ b/scripts/start-datastore.sh @@ -1 +1 @@ -gcloud beta emulators datastore start --project=spine-dev --host-port=localhost:8080 --consistency 1.0 --no-store-on-disk +gcloud beta emulators datastore start --project=spine-dev --consistency 1.0 --no-store-on-disk diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java index a90df157e..c1fa1f44f 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java @@ -21,47 +21,21 @@ package io.spine.testing.server.storage.datastore; import com.google.cloud.datastore.Datastore; -import com.google.cloud.datastore.DatastoreOptions; import com.google.common.flogger.FluentLogger; import io.spine.annotation.Internal; import io.spine.server.storage.datastore.DatastoreStorageFactory; import io.spine.server.storage.datastore.DatastoreWrapper; import io.spine.server.storage.datastore.type.DatastoreTypeRegistryFactory; -import org.checkerframework.checker.nullness.qual.MonotonicNonNull; /** - * Creates storages based on the local Google {@link Datastore}. + * A test implementation of the {@link DatastoreStorageFactory}. + * + *

Wraps the datastore with an instance of {@link TestDatastoreWrapper} and provides additional + * clean up {@link #tearDown() methods}. */ public class TestDatastoreStorageFactory extends DatastoreStorageFactory { private static final FluentLogger logger = FluentLogger.forEnclosingClass(); - private static @MonotonicNonNull TestDatastoreStorageFactory instance = null; - - /** - * Returns a default factory instance. A {@link Datastore} is created with - * default {@link DatastoreOptions}: - * - *

Dataset name: {@code spine-dev} - * - *

Connects to a localhost Datastore emulator. - */ - public static synchronized TestDatastoreStorageFactory defaultInstance() { - try { - if (instance == null) { - instance = createInstance(); - } - return instance; - } catch (Throwable e) { - logger.atSevere() - .withCause(e) - .log("Failed to initialize local datastore factory."); - throw new IllegalStateException(e); - } - } - - private static TestDatastoreStorageFactory createInstance() { - return new TestDatastoreStorageFactory(TestDatastores.local()); - } protected TestDatastoreStorageFactory(Datastore datastore) { super(DatastoreStorageFactory @@ -71,6 +45,14 @@ protected TestDatastoreStorageFactory(Datastore datastore) { ); } + public static TestDatastoreStorageFactory local() { + return basedOn(TestDatastores.local()); + } + + public static TestDatastoreStorageFactory basedOn(Datastore datastore) { + return new TestDatastoreStorageFactory(datastore); + } + @Internal @Override protected DatastoreWrapper createDatastoreWrapper(boolean multitenant) { diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index 5847cab11..39e1ca445 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -20,108 +20,86 @@ package io.spine.testing.server.storage.datastore; +import com.google.auth.Credentials; import com.google.auth.oauth2.ServiceAccountCredentials; import com.google.cloud.NoCredentials; import com.google.cloud.datastore.Datastore; import com.google.cloud.datastore.DatastoreOptions; +import io.spine.io.Resource; import io.spine.logging.Logging; import io.spine.server.storage.datastore.ProjectId; -import java.io.BufferedInputStream; import java.io.IOException; import java.io.InputStream; import static com.google.auth.oauth2.ServiceAccountCredentials.fromStream; +import static io.spine.io.Resource.file; +import static io.spine.util.Exceptions.newIllegalArgumentException; +import static java.lang.String.format; -/** - * Provides test {@link Datastore} instances. - */ -public final class TestDatastores { +public final class TestDatastores implements Logging { + + /** + * The default port to which the local Datastore emulator is bound. + * + *

See + * {@code gcloud} docs. + */ + private static final int DEFAULT_EMULATOR_PORT = 8081; + private static final String LOCALHOST = "localhost"; - @SuppressWarnings("DuplicateStringLiteralInspection") // Project name duplication. - private static final ProjectId TEST_PROJECT_ID = ProjectId.of("spine-dev"); + private static final ProjectId TEST_PROJECT_ID = ProjectId.of("test-project"); - /** Prevent this test utility class from being instantiated. */ + /** Prevents instantiation of this utility class. */ private TestDatastores() { } - /** - * Obtains Datastore instance used for testing on a developer's workstation. - */ public static Datastore local() { - return Local.INSTANCE.getService(); + return local(DEFAULT_EMULATOR_PORT); } - /** - * Obtains Datastore instance used for testing in a CI environment. - */ - public static Datastore remote() { - return Ci.INSTANCE.getService(); + public static Datastore local(int port) { + String address = format("%s:%s", LOCALHOST, port); + return local(address); } - /** - * Obtains ProjectId of the test environment. - */ - public static ProjectId projectId() { - return TEST_PROJECT_ID; + public static Datastore local(String address) { + DatastoreOptions options = DatastoreOptions + .newBuilder() + .setProjectId(TEST_PROJECT_ID.value()) + .setHost(address) + .setCredentials(NoCredentials.getInstance()) + .build(); + Datastore datastore = options.getService(); + return datastore; } - /** - * Abstract base for options factories. - */ - private abstract static class Options { - - private final DatastoreOptions.Builder builder; - - private Options() { - builder = DatastoreOptions.newBuilder() - .setProjectId(projectId().getValue()); - } - - final DatastoreOptions.Builder builder() { - return builder; - } - - final DatastoreOptions create() { - return builder.build(); - } + public static Datastore remote(String serviceAccountPath) { + return remote(file(serviceAccountPath)); } - /** - * Local Datastore options used on developers' machines. - */ - private static final class Local extends Options { - - private static final String DEFAULT_HOST = "localhost:8080"; - private static final DatastoreOptions INSTANCE = new Local().create(); - - private Local() { - super(); - builder().setHost(DEFAULT_HOST); - builder().setCredentials(NoCredentials.getInstance()); + public static Datastore remote(Resource serviceAccount) { + try { + Credentials credentials = credentialsFrom(serviceAccount); + DatastoreOptions options = DatastoreOptions + .newBuilder() + .setCredentials(credentials) + .build(); + Datastore datastore = options.getService(); + return datastore; + } catch (IOException e) { + throw newIllegalArgumentException( + e, "Cannot find the credentials file `%s`.", serviceAccount); } } - /** - * Options used to run tests in CI environment, which uses connection to - * a real Datastore instance in the testing Google Cloud environment. - */ - @SuppressWarnings("NewClassNamingConvention") - private static final class Ci extends Options implements Logging { - - private static final String CREDENTIALS_FILE_PATH = "/spine-dev.json"; - private static final DatastoreOptions INSTANCE = new Ci().create(); + private static Credentials credentialsFrom(Resource serviceAccount) throws IOException { + InputStream is = serviceAccount.open(); + ServiceAccountCredentials credentials = fromStream(is); + return credentials; + } - private Ci() { - super(); - try { - InputStream is = TestDatastores.class.getResourceAsStream(CREDENTIALS_FILE_PATH); - BufferedInputStream bufferedStream = new BufferedInputStream(is); - ServiceAccountCredentials credentials = fromStream(bufferedStream); - builder().setCredentials(credentials); - } catch (IOException e) { - _warn().log("Cannot find the credentials file `%s`.", CREDENTIALS_FILE_PATH); - } - } + public static ProjectId testProjectId() { + return TEST_PROJECT_ID; } } From 9945eecefd6b920bd94fae23cb4c373f45689ffd Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 17:28:04 +0300 Subject: [PATCH 06/30] Remove `TestEnvironment` from `testutil-gcloud` It's not `gcloud`-related. Its place is probably in `base` but for now every project does this thing separately in its own way. --- .../server/storage/datastore/DatastoreStorageFactoryTest.java | 2 +- .../io/spine/server/storage/datastore/DatastoreWrapperTest.java | 2 +- .../datastore/DsAggregateStorageLifecycleHandlingTest.java | 2 +- .../spine/server/storage/datastore/DsAggregateStorageTest.java | 2 +- .../spine/server/storage/datastore/DsProjectionStorageTest.java | 2 +- .../spine/server/storage/datastore/DsPropertyStorageTest.java | 2 +- .../io/spine/server/storage/datastore/DsRecordStorageTest.java | 2 +- .../spine/server/storage/datastore/given}/TestEnvironment.java | 2 +- 8 files changed, 8 insertions(+), 8 deletions(-) rename {testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore => datastore/src/test/java/io/spine/server/storage/datastore/given}/TestEnvironment.java (97%) diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java index 1e776821f..8982ea5c7 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java @@ -35,9 +35,9 @@ import io.spine.server.entity.storage.ColumnTypeRegistry; import io.spine.server.storage.RecordStorage; import io.spine.server.storage.StorageFactory; +import io.spine.server.storage.datastore.given.TestEnvironment; import io.spine.server.storage.datastore.type.DatastoreTypeRegistryFactory; import io.spine.test.storage.Project; -import io.spine.testing.server.storage.datastore.TestEnvironment; import io.spine.type.TypeName; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java index 718912e76..a084aa4fb 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java @@ -55,10 +55,10 @@ import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.ensureNamespace; import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.localDatastore; import static io.spine.server.storage.datastore.given.DatastoreWrapperTestEnv.remoteDatastore; +import static io.spine.server.storage.datastore.given.TestEnvironment.runsOnCi; import static io.spine.server.storage.datastore.tenant.TestNamespaceSuppliers.multitenant; import static io.spine.server.storage.datastore.tenant.TestNamespaceSuppliers.singleTenant; import static io.spine.testing.server.storage.datastore.TestDatastoreWrapper.wrap; -import static io.spine.testing.server.storage.datastore.TestEnvironment.runsOnCi; import static java.lang.String.format; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertFalse; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java index 41b639d8f..3d89151e6 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageLifecycleHandlingTest.java @@ -30,8 +30,8 @@ import org.junit.jupiter.api.BeforeAll; import org.junit.jupiter.api.DisplayName; +import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.local; -import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; @DisplayName("`DsAggregateStorage` lifecycle handling should") class DsAggregateStorageLifecycleHandlingTest diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java index ce5a54c4a..a5bd97315 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java @@ -71,8 +71,8 @@ import static io.spine.server.aggregate.given.Given.CommandMessage.addTask; import static io.spine.server.storage.datastore.DatastoreWrapper.MAX_ENTITIES_PER_WRITE_REQUEST; import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.datastoreFactory; +import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.local; -import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertNull; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java index 57b4f177e..fd11e0b51 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsProjectionStorageTest.java @@ -36,8 +36,8 @@ import org.junit.jupiter.api.DisplayName; import static io.spine.base.Time.currentTime; +import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.local; -import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; @DisplayName("`DsProjectionStorage` should") class DsProjectionStorageTest extends ProjectionStorageTest { diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java index 918ed5474..2bcfa0b5d 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsPropertyStorageTest.java @@ -23,8 +23,8 @@ import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; +import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; import static io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory.local; -import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; import static org.junit.jupiter.api.Assertions.assertNotNull; @DisplayName("`DsPropertyStorage` should") diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java index acb0b7cb5..19eb72a5e 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java @@ -116,7 +116,7 @@ import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.recordIds; import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.sortedIds; import static io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.sortedValues; -import static io.spine.testing.server.storage.datastore.TestEnvironment.singleTenantSpec; +import static io.spine.server.storage.datastore.given.TestEnvironment.singleTenantSpec; import static java.util.Collections.singletonList; import static java.util.stream.Collectors.toList; import static org.junit.Assert.assertFalse; diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestEnvironment.java b/datastore/src/test/java/io/spine/server/storage/datastore/given/TestEnvironment.java similarity index 97% rename from testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestEnvironment.java rename to datastore/src/test/java/io/spine/server/storage/datastore/given/TestEnvironment.java index e17c2255c..617934664 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestEnvironment.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/given/TestEnvironment.java @@ -18,7 +18,7 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.testing.server.storage.datastore; +package io.spine.server.storage.datastore.given; import io.spine.server.ContextSpec; From 5fbc495045663d33d9e3aff832b3a2c7a7469cce Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 17:36:51 +0300 Subject: [PATCH 07/30] Remove `CountingDatastoreWrapper` from `testutil-gcloud` It's too specific to be in a test lib. Users are better off implementing their own versions of the `TestDatastoreWrapper`. --- .../spine/server/storage/datastore/DsAggregateStorageTest.java | 2 +- .../io/spine/server/storage/datastore/DsRecordStorageTest.java | 2 +- .../storage/datastore/given}/CountingDatastoreWrapper.java | 3 ++- 3 files changed, 4 insertions(+), 3 deletions(-) rename {testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore => datastore/src/test/java/io/spine/server/storage/datastore/given}/CountingDatastoreWrapper.java (95%) diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java index a5bd97315..dea6e16c8 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsAggregateStorageTest.java @@ -40,6 +40,7 @@ import io.spine.server.aggregate.Snapshot; import io.spine.server.aggregate.given.repo.ProjectAggregate; import io.spine.server.entity.Entity; +import io.spine.server.storage.datastore.given.CountingDatastoreWrapper; import io.spine.server.storage.datastore.given.aggregate.ProjectAggregateRepository; import io.spine.server.type.CommandEnvelope; import io.spine.test.aggregate.Project; @@ -49,7 +50,6 @@ import io.spine.testdata.Sample; import io.spine.testing.client.TestActorRequestFactory; import io.spine.testing.server.TestEventFactory; -import io.spine.testing.server.storage.datastore.CountingDatastoreWrapper; import io.spine.testing.server.storage.datastore.SpyStorageFactory; import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import org.junit.jupiter.api.AfterAll; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java index 19eb72a5e..15878a644 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DsRecordStorageTest.java @@ -44,6 +44,7 @@ import io.spine.server.storage.RecordStorageTest; import io.spine.server.storage.StorageFactory; import io.spine.server.storage.datastore.given.CollegeEntity; +import io.spine.server.storage.datastore.given.CountingDatastoreWrapper; import io.spine.server.storage.datastore.given.DsRecordStorageTestEnv; import io.spine.server.storage.datastore.given.DsRecordStorageTestEnv.EntityWithCustomColumnName; import io.spine.server.storage.datastore.given.TestConstCounterEntity; @@ -53,7 +54,6 @@ import io.spine.test.storage.Project; import io.spine.test.storage.ProjectId; import io.spine.test.storage.Task; -import io.spine.testing.server.storage.datastore.CountingDatastoreWrapper; import io.spine.testing.server.storage.datastore.SpyStorageFactory; import io.spine.testing.server.storage.datastore.TestDatastoreStorageFactory; import io.spine.type.TypeUrl; diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/CountingDatastoreWrapper.java b/datastore/src/test/java/io/spine/server/storage/datastore/given/CountingDatastoreWrapper.java similarity index 95% rename from testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/CountingDatastoreWrapper.java rename to datastore/src/test/java/io/spine/server/storage/datastore/given/CountingDatastoreWrapper.java index f3b436caf..29eaf21cc 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/CountingDatastoreWrapper.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/given/CountingDatastoreWrapper.java @@ -18,13 +18,14 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package io.spine.testing.server.storage.datastore; +package io.spine.server.storage.datastore.given; import com.google.cloud.datastore.Datastore; import com.google.cloud.datastore.Entity; import com.google.cloud.datastore.Key; import com.google.cloud.datastore.StructuredQuery; import io.spine.server.storage.datastore.DsQueryIterator; +import io.spine.testing.server.storage.datastore.TestDatastoreWrapper; import org.checkerframework.checker.nullness.qual.Nullable; import java.util.Collection; From 09fc2f843e5d54a9ed0d2bbbd7f7459727b3be28 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 17:37:22 +0300 Subject: [PATCH 08/30] Remove an unused method --- .../server/storage/datastore/TestNamespaceSuppliers.java | 5 ----- 1 file changed, 5 deletions(-) diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java index 86189b014..7918ddece 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java @@ -21,7 +21,6 @@ package io.spine.testing.server.storage.datastore; import io.spine.server.storage.datastore.tenant.NamespaceSupplier; -import io.spine.server.storage.datastore.tenant.NsConverterFactory; final class TestNamespaceSuppliers { @@ -31,8 +30,4 @@ private TestNamespaceSuppliers() { static NamespaceSupplier singleTenant() { return NamespaceSupplier.singleTenant(); } - - static NamespaceSupplier multitenant() { - return NamespaceSupplier.multitenant(NsConverterFactory.defaults()); - } } From 0f500f76ccac8b90edf2592b5e8cba23548bfae9 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 18:34:42 +0300 Subject: [PATCH 09/30] Fix kind cache not handling multiple project IDs at runtime correctly --- .../storage/datastore/DatastoreWrapper.java | 51 +++++++++++++++++-- .../storage/datastore/DsMessageStorage.java | 2 +- .../server/storage/datastore/Indexes.java | 2 +- .../spine/server/storage/datastore/Kind.java | 33 +++--------- .../storage/datastore/QueryWithFilter.java | 2 +- .../datastore/tenant/NamespaceIndex.java | 2 +- .../datastore/DatastoreWrapperTest.java | 4 +- .../server/storage/datastore/KindTest.java | 14 ++--- license-report.md | 6 +-- .../datastore/TestDatastoreWrapper.java | 2 +- 10 files changed, 70 insertions(+), 48 deletions(-) diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java index b908ca35d..bee38275c 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java @@ -48,6 +48,7 @@ import java.util.Iterator; import java.util.List; import java.util.Map; +import java.util.Objects; import static com.google.common.base.Preconditions.checkArgument; import static com.google.common.base.Preconditions.checkNotNull; @@ -76,7 +77,7 @@ public class DatastoreWrapper implements Logging { private static final int MAX_KEYS_PER_READ_REQUEST = 1000; static final int MAX_ENTITIES_PER_WRITE_REQUEST = 500; - private static final Map keyFactories = new HashMap<>(); + private static final Map keyFactories = new HashMap<>(); private static final Key[] EMPTY_KEY_ARRAY = new Key[0]; @@ -503,7 +504,8 @@ public boolean isTransactionActive() { * @return an instance of {@link KeyFactory} for given kind */ public KeyFactory keyFactory(Kind kind) { - KeyFactory keyFactory = keyFactories.get(kind); + DatastoreKind datastoreKind = new DatastoreKind(projectId(), kind); + KeyFactory keyFactory = keyFactories.get(datastoreKind); if (keyFactory == null) { keyFactory = initKeyFactory(kind); } @@ -528,11 +530,19 @@ public Datastore datastore() { private KeyFactory initKeyFactory(Kind kind) { KeyFactory keyFactory = datastore.newKeyFactory() - .setKind(kind.getValue()); - keyFactories.put(kind, keyFactory); + .setKind(kind.value()); + DatastoreKind datastoreKind = new DatastoreKind(projectId(), kind); + keyFactories.put(datastoreKind, keyFactory); return keyFactory; } + private ProjectId projectId() { + String projectId = datastore.getOptions() + .getProjectId(); + ProjectId result = ProjectId.of(projectId); + return result; + } + /** * Reads big number of records. * @@ -587,4 +597,37 @@ private Namespace currentNamespace() { private void writeSmallBulk(Entity[] entities) { actor.put(entities); } + + /** + * A Datastore {@link Kind} by project ID. + */ + private static class DatastoreKind { + + private final ProjectId projectId; + private final Kind kind; + + private DatastoreKind(ProjectId projectId, Kind kind) { + this.projectId = projectId; + this.kind = kind; + } + + @SuppressWarnings("EqualsGetClass") // The class is effectively final. + @Override + public boolean equals(Object o) { + if (this == o) { + return true; + } + if (o == null || getClass() != o.getClass()) { + return false; + } + DatastoreKind kind1 = (DatastoreKind) o; + return Objects.equals(projectId, kind1.projectId) && + Objects.equals(kind, kind1.kind); + } + + @Override + public int hashCode() { + return Objects.hash(projectId, kind); + } + } } diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DsMessageStorage.java b/datastore/src/main/java/io/spine/server/storage/datastore/DsMessageStorage.java index 61ca7066b..62bf0fb82 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DsMessageStorage.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DsMessageStorage.java @@ -200,7 +200,7 @@ public void writeAll(Iterable messages) { */ Iterator readAll(EntityQuery.Builder queryBuilder, int readBatchSize) { StructuredQuery query = - queryBuilder.setKind(kind.getValue()) + queryBuilder.setKind(kind.value()) .build(); Iterator iterator = datastore.readAll(query, readBatchSize); Iterator transformed = diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/Indexes.java b/datastore/src/main/java/io/spine/server/storage/datastore/Indexes.java index 299707bc8..5b8caad3e 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/Indexes.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/Indexes.java @@ -63,7 +63,7 @@ static Iterator indexIterator(DatastoreWrapper datastore, Kind kind, Clas checkNotNull(idType); StructuredQuery query = Query.newKeyQueryBuilder() - .setKind(kind.getValue()) + .setKind(kind.value()) .build(); Iterator allEntities = datastore.read(query); Iterator idIterator = Streams.stream(allEntities) diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/Kind.java b/datastore/src/main/java/io/spine/server/storage/datastore/Kind.java index 31e11628c..c0720c249 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/Kind.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/Kind.java @@ -20,12 +20,12 @@ package io.spine.server.storage.datastore; -import com.google.common.base.Objects; import com.google.protobuf.Descriptors.Descriptor; import com.google.protobuf.Message; import io.spine.annotation.Internal; import io.spine.type.TypeName; import io.spine.type.TypeUrl; +import io.spine.value.StringTypeValue; import static com.google.common.base.Preconditions.checkArgument; import static com.google.common.base.Preconditions.checkNotNull; @@ -34,7 +34,9 @@ * A data transfer object representing a Datastore * kind. */ -public final class Kind { +public final class Kind extends StringTypeValue { + + private static final long serialVersionUID = 0L; private static final String INVALID_KIND_ERROR_MESSAGE = "Datastore kind cannot start with \"__\". See " + @@ -44,10 +46,8 @@ public final class Kind { private static final String NAMESPACE_KIND = "__namespace__"; - private final String value; - private Kind(String value) { - this.value = checkValidKind(value); + super(checkValidKind(value)); } /** @@ -59,8 +59,8 @@ private Kind(String value) { * the flag showing that the {@code Kind} is ancillary; must be set to {@code true} */ private Kind(String value, boolean ancillary) { + super(value); checkArgument(ancillary); - this.value = value; } public static Kind of(String value) { @@ -92,30 +92,9 @@ public static Kind ofNamespace() { return new Kind(NAMESPACE_KIND, true); } - public String getValue() { - return value; - } - private static String checkValidKind(String kind) { checkNotNull(kind); checkArgument(!kind.startsWith(FORBIDDEN_PREFIX), INVALID_KIND_ERROR_MESSAGE); return kind; } - - @Override - public boolean equals(Object o) { - if (this == o) { - return true; - } - if (o == null || getClass() != o.getClass()) { - return false; - } - Kind kind = (Kind) o; - return Objects.equal(getValue(), kind.getValue()); - } - - @Override - public int hashCode() { - return Objects.hashCode(getValue()); - } } diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/QueryWithFilter.java b/datastore/src/main/java/io/spine/server/storage/datastore/QueryWithFilter.java index 88bf58610..6096642a4 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/QueryWithFilter.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/QueryWithFilter.java @@ -46,7 +46,7 @@ final class QueryWithFilter implements Function run() { Query query = Query.newKeyQueryBuilder() - .setKind(NAMESPACE_KIND.getValue()) + .setKind(NAMESPACE_KIND.value()) .build(); Iterator result = datastore.run(query); return result; diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java index a084aa4fb..76d02115d 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreWrapperTest.java @@ -172,7 +172,7 @@ void testBigBulkRead() throws InterruptedException { Thread.sleep(bulkSize * 3L); StructuredQuery query = newEntityQueryBuilder() - .setKind(GENERIC_ENTITY_KIND.getValue()) + .setKind(GENERIC_ENTITY_KIND.value()) .build(); Collection readEntities = newArrayList(wrapper.read(query)); assertEquals(entities.size(), readEntities.size()); @@ -386,7 +386,7 @@ void testLazyIterator() { wrapper.createOrUpdate(expctedEntities); StructuredQuery query = newEntityQueryBuilder() - .setKind(GENERIC_ENTITY_KIND.getValue()) + .setKind(GENERIC_ENTITY_KIND.value()) .build(); Iterator result = wrapper.read(query); diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/KindTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/KindTest.java index 6c94da00b..51de4916a 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/KindTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/KindTest.java @@ -78,7 +78,7 @@ void testCheckValidity() { void testFromString() { String type = "my.custom.type"; Kind kind = Kind.of(type); - assertEquals(type, kind.getValue()); + assertEquals(type, kind.value()); } @Test @@ -87,9 +87,9 @@ void testFromTypeUrl() { Descriptors.Descriptor descriptor = Any.getDescriptor(); TypeUrl type = TypeUrl.from(descriptor); Kind kind = Kind.of(type); - assertEquals(descriptor.getFullName(), kind.getValue()); + assertEquals(descriptor.getFullName(), kind.value()); assertEquals(type.toTypeName() - .value(), kind.getValue()); + .value(), kind.value()); } @Test @@ -97,7 +97,7 @@ void testFromTypeUrl() { void testFromDescriptor() { Descriptors.Descriptor descriptor = Any.getDescriptor(); Kind kind = Kind.of(descriptor); - assertEquals(descriptor.getFullName(), kind.getValue()); + assertEquals(descriptor.getFullName(), kind.value()); } @Test @@ -106,7 +106,7 @@ void testFromMessage() { Message message = Any.getDefaultInstance(); Kind kind = Kind.of(message); assertEquals(message.getDescriptorForType() - .getFullName(), kind.getValue()); + .getFullName(), kind.value()); } @Test @@ -115,7 +115,7 @@ void testFromTypeName() { Descriptors.Descriptor descriptor = Any.getDescriptor(); TypeName type = TypeName.from(descriptor); Kind kind = Kind.of(type); - assertEquals(descriptor.getFullName(), kind.getValue()); - assertEquals(type.value(), kind.getValue()); + assertEquals(descriptor.getFullName(), kind.value()); + assertEquals(type.value(), kind.value()); } } diff --git a/license-report.md b/license-report.md index d2eeb4f71..dfd3f426d 100644 --- a/license-report.md +++ b/license-report.md @@ -734,7 +734,7 @@ The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 17:20:30 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 18:31:16 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -1474,7 +1474,7 @@ This report was generated on **Tue Oct 01 17:20:30 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 17:20:43 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 18:31:29 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -2234,4 +2234,4 @@ This report was generated on **Tue Oct 01 17:20:43 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 17:20:55 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file +This report was generated on **Tue Oct 01 18:31:48 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java index fa5718f50..792c3540b 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java @@ -72,7 +72,7 @@ public static TestDatastoreWrapper wrap(Datastore datastore, boolean waitForCons @Override public KeyFactory keyFactory(Kind kind) { - kindsCache.add(kind.getValue()); + kindsCache.add(kind.value()); return super.keyFactory(kind); } From 10bcf57ffb2d342f4a9a7c4fb9df43077c6cc157 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 19:19:52 +0300 Subject: [PATCH 10/30] Add some doc Also did a minor refactoring. --- .../DatastoreStorageFactoryBuilderTest.java | 4 +-- .../DatastoreStorageFactoryTest.java | 4 +-- .../datastore/tenant/NamespaceTest.java | 4 +-- .../datastore/type/DsColumnTypesTest.java | 4 +-- license-report.md | 6 ++-- .../storage/datastore/SpyStorageFactory.java | 11 +++++- .../TestDatastoreStorageFactory.java | 14 ++++++-- .../datastore/TestDatastoreWrapper.java | 25 +++++++++---- .../storage/datastore/TestDatastores.java | 36 ++++++++++++++++--- .../datastore/TestNamespaceSuppliers.java | 33 ----------------- 10 files changed, 83 insertions(+), 58 deletions(-) delete mode 100644 testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java index 8acb3bb6a..0ac46c471 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java @@ -40,7 +40,7 @@ import static io.spine.testing.DisplayNames.HAVE_PARAMETERLESS_CTOR; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; import static io.spine.testing.Tests.assertHasPrivateParameterlessCtor; -import static io.spine.testing.server.storage.datastore.TestDatastores.testProjectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.localProjectId; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertThrows; @@ -102,7 +102,7 @@ class Namespaces { void setUp() { builder = DatastoreOptions .newBuilder() - .setProjectId(testProjectId().getValue()); + .setProjectId(localProjectId().getValue()); } @Test diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java index 8982ea5c7..b84bde0a6 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java @@ -47,7 +47,7 @@ import static io.spine.server.tenant.TenantAwareRunner.with; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; import static io.spine.testing.server.storage.datastore.TestDatastores.local; -import static io.spine.testing.server.storage.datastore.TestDatastores.testProjectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.localProjectId; import static org.junit.jupiter.api.Assertions.assertNotEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertSame; @@ -177,7 +177,7 @@ private static Key.Builder whiteForTenant(DsPropertyStorage storage, TenantId te with(tenant).run( () -> storage.write(recordId, message) ); - return Key.newBuilder(testProjectId().getValue(), + return Key.newBuilder(localProjectId().getValue(), TypeName.of(message) .value(), recordId.getValue()); diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java index 7c1456d78..ce3dade86 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java @@ -31,7 +31,7 @@ import org.junit.jupiter.api.Test; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; -import static io.spine.testing.server.storage.datastore.TestDatastores.testProjectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.localProjectId; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; @@ -44,7 +44,7 @@ class NamespaceTest { @Test @DisplayName(NOT_ACCEPT_NULLS) void testNulls() { - ProjectId defaultProjectId = testProjectId(); + ProjectId defaultProjectId = localProjectId(); Key defaultKey = Key.newBuilder(defaultProjectId.getValue(), "kind", "name") .build(); new NullPointerTester() diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java index 57575bf84..8657656bb 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java @@ -40,7 +40,7 @@ import static io.spine.server.storage.datastore.type.DsColumnTypes.timestampType; import static io.spine.testing.DisplayNames.HAVE_PARAMETERLESS_CTOR; import static io.spine.testing.Tests.assertHasPrivateParameterlessCtor; -import static io.spine.testing.server.storage.datastore.TestDatastores.testProjectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.localProjectId; @DisplayName("DsColumnTypes should") class DsColumnTypesTest { @@ -225,7 +225,7 @@ private void setDatastoreType(DatastoreColumnType type, } private static BaseEntity.Builder entityBuilder() { - String projectId = testProjectId().value(); + String projectId = localProjectId().value(); Key key = Key.newBuilder(projectId, "some-entity-kind", "some-name") .build(); Entity.Builder builder = Entity.newBuilder(key); diff --git a/license-report.md b/license-report.md index dfd3f426d..2264832c6 100644 --- a/license-report.md +++ b/license-report.md @@ -734,7 +734,7 @@ The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 18:31:16 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 19:17:26 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -1474,7 +1474,7 @@ This report was generated on **Tue Oct 01 18:31:16 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 18:31:29 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 19:17:38 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -2234,4 +2234,4 @@ This report was generated on **Tue Oct 01 18:31:29 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 18:31:48 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file +This report was generated on **Tue Oct 01 19:17:51 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java index e5167dedc..98bd808a6 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java @@ -22,6 +22,8 @@ import io.spine.server.storage.datastore.DatastoreWrapper; +import static com.google.common.base.Preconditions.checkNotNull; + /** * A {@link TestDatastoreStorageFactory} which allows to inject a custom {@link DatastoreWrapper}. */ @@ -29,12 +31,19 @@ public final class SpyStorageFactory extends TestDatastoreStorageFactory { private static DatastoreWrapper injectedWrapper = null; + /** + * Injects a given {@code DatastoreWrapper} into the storage factory. + * + *

All storages created by this factory will operate based on the given wrapper. + * + *

Should be called before the {@code SpyStorageFactory} instance is created. + */ public static void injectWrapper(DatastoreWrapper wrapper) { injectedWrapper = wrapper; } public SpyStorageFactory() { - super(injectedWrapper.datastore()); + super(checkNotNull(injectedWrapper).datastore()); } @Override diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java index c1fa1f44f..fdf96a754 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java @@ -31,7 +31,7 @@ * A test implementation of the {@link DatastoreStorageFactory}. * *

Wraps the datastore with an instance of {@link TestDatastoreWrapper} and provides additional - * clean up {@link #tearDown() methods}. + * clean up {@linkplain #tearDown() methods}. */ public class TestDatastoreStorageFactory extends DatastoreStorageFactory { @@ -45,10 +45,18 @@ protected TestDatastoreStorageFactory(Datastore datastore) { ); } + /** + * Creates a new instance which works with a local Datastore emulator. + * + *

A shortcut for {@code basedOn(TestDatastores.local())}. + */ public static TestDatastoreStorageFactory local() { return basedOn(TestDatastores.local()); } + /** + * Creates a new factory instance which wraps the given Datastore. + */ public static TestDatastoreStorageFactory basedOn(Datastore datastore) { return new TestDatastoreStorageFactory(datastore); } @@ -71,11 +79,11 @@ public void setUp() { /** * Clears all data in the local Datastore. * - *

May be effectively the same as {@link #clear()}. + *

Is effectively the same as {@link #clear()}. * *

NOTE: does not stop the server but just deletes all records. * - *

Equivalent to dropping all tables in an SQL-base storage. + *

Equivalent to dropping all tables in an SQL-based storage. */ public void tearDown() { clear(); diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java index 792c3540b..a1660604e 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java @@ -28,6 +28,7 @@ import com.google.cloud.datastore.StructuredQuery; import io.spine.server.storage.datastore.DatastoreWrapper; import io.spine.server.storage.datastore.Kind; +import io.spine.server.storage.datastore.tenant.NamespaceSupplier; import java.util.ArrayList; import java.util.Collection; @@ -43,17 +44,20 @@ */ public class TestDatastoreWrapper extends DatastoreWrapper { - // Default time to wait before each read operation to ensure the data is consistent. - // NOTE: enabled only if {@link #shouldWaitForConsistency} is {@code true}. + /** + * Default time to wait before each read operation to ensure the data is consistent. + * + *

NOTE: enabled only if {@link #waitForConsistency} is {@code true}. + */ private static final int CONSISTENCY_AWAIT_TIME_MS = 10; private static final int CONSISTENCY_AWAIT_ITERATIONS = 20; /** - * Due to eventual consistency, {@link #dropTable(String) is performed iteratively until + * Due to eventual consistency, {@linkplain #dropTable(String) is performed iteratively until * the table has no records}. * - * This constant represents the maximum number of cleanup attempts before the execution - * is continued + *

This constant represents the maximum number of cleanup attempts before the execution + * is continued. */ private static final int MAX_CLEANUP_ATTEMPTS = 5; @@ -62,10 +66,19 @@ public class TestDatastoreWrapper extends DatastoreWrapper { private final boolean waitForConsistency; protected TestDatastoreWrapper(Datastore datastore, boolean waitForConsistency) { - super(datastore, TestNamespaceSuppliers.singleTenant()); + super(datastore, NamespaceSupplier.singleTenant()); this.waitForConsistency = waitForConsistency; } + /** + * Wraps a given Datastore. + * + *

The {@code waitForConsistency} parameter allows to add a delay to each write operation to + * compensate for the eventual consistency of the storage. + * + *

The {@code waitForConsistency} parameter should be set to {@code false} when wrapping a + * local Datastore emulator. + */ public static TestDatastoreWrapper wrap(Datastore datastore, boolean waitForConsistency) { return new TestDatastoreWrapper(datastore, waitForConsistency); } diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index 39e1ca445..4818872f2 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -37,6 +37,9 @@ import static io.spine.util.Exceptions.newIllegalArgumentException; import static java.lang.String.format; +/** + * A factory of test {@link Datastore} instances. + */ public final class TestDatastores implements Logging { /** @@ -48,25 +51,39 @@ public final class TestDatastores implements Logging { private static final int DEFAULT_EMULATOR_PORT = 8081; private static final String LOCALHOST = "localhost"; - private static final ProjectId TEST_PROJECT_ID = ProjectId.of("test-project"); + /** + * The project ID which is used when running on local Datastore emulator. + */ + private static final ProjectId LOCAL_PROJECT_ID = ProjectId.of("test-project"); /** Prevents instantiation of this utility class. */ private TestDatastores() { } + /** + * Creates a {@link Datastore} connected to the local Datastore emulator at + * {@link #DEFAULT_EMULATOR_PORT}. + */ public static Datastore local() { return local(DEFAULT_EMULATOR_PORT); } + /** + * Creates a {@link Datastore} connected to the local Datastore emulator at the specified port. + */ public static Datastore local(int port) { String address = format("%s:%s", LOCALHOST, port); return local(address); } + /** + * Creates a {@link Datastore} connected to the local Datastore emulator at the specified + * address. + */ public static Datastore local(String address) { DatastoreOptions options = DatastoreOptions .newBuilder() - .setProjectId(TEST_PROJECT_ID.value()) + .setProjectId(LOCAL_PROJECT_ID.value()) .setHost(address) .setCredentials(NoCredentials.getInstance()) .build(); @@ -74,10 +91,21 @@ public static Datastore local(String address) { return datastore; } + /** + * Creates a {@link Datastore} connected to the remote Google Cloud Datastore described by the + * given service account resource. + * + *

The {@code serviceAccountPath} is a path to the resource file, specified relative to the + * classpath. + */ public static Datastore remote(String serviceAccountPath) { return remote(file(serviceAccountPath)); } + /** + * Creates a {@link Datastore} connected to the remote Google Cloud Datastore described by the + * given service account resource. + */ public static Datastore remote(Resource serviceAccount) { try { Credentials credentials = credentialsFrom(serviceAccount); @@ -99,7 +127,7 @@ private static Credentials credentialsFrom(Resource serviceAccount) throws IOExc return credentials; } - public static ProjectId testProjectId() { - return TEST_PROJECT_ID; + public static ProjectId localProjectId() { + return LOCAL_PROJECT_ID; } } diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java deleted file mode 100644 index 7918ddece..000000000 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestNamespaceSuppliers.java +++ /dev/null @@ -1,33 +0,0 @@ -/* - * Copyright 2019, TeamDev. All rights reserved. - * - * Redistribution and use in source and/or binary forms, with or without - * modification, must retain the above copyright notice and the following - * disclaimer. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, - * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT - * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, - * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY - * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE - * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -package io.spine.testing.server.storage.datastore; - -import io.spine.server.storage.datastore.tenant.NamespaceSupplier; - -final class TestNamespaceSuppliers { - - private TestNamespaceSuppliers() { - } - - static NamespaceSupplier singleTenant() { - return NamespaceSupplier.singleTenant(); - } -} From e1b78a3698be4066e315539313ffa418e90f8292 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 20:58:22 +0300 Subject: [PATCH 11/30] Add tests Also did minor refactoring and added additional checks to the public methods. --- .travis.yml | 1 + .../datastore/DatastoreStorageFactory.java | 4 +- .../storage/datastore/DatastoreWrapper.java | 2 +- .../storage/datastore/SpyStorageFactory.java | 10 +- .../TestDatastoreStorageFactory.java | 18 +++- .../datastore/TestDatastoreWrapper.java | 14 ++- .../storage/datastore/TestDatastores.java | 16 ++- .../datastore/SpyStorageFactoryTest.java | 61 ++++++++++++ .../TestDatastoreStorageFactoryTest.java | 78 +++++++++++++++ .../datastore/TestDatastoreWrapperTest.java | 91 +++++++++++++++++ .../storage/datastore/TestDatastoresTest.java | 99 +++++++++++++++++++ .../given/ATestDatastoreWrapper.java | 47 +++++++++ .../storage/datastore/given/AnEntity.java | 55 +++++++++++ .../storage/datastore/given/package-info.java | 31 ++++++ 14 files changed, 510 insertions(+), 17 deletions(-) create mode 100644 testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/SpyStorageFactoryTest.java create mode 100644 testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactoryTest.java create mode 100644 testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapperTest.java create mode 100644 testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java create mode 100644 testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/ATestDatastoreWrapper.java create mode 100644 testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/AnEntity.java create mode 100644 testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/package-info.java diff --git a/.travis.yml b/.travis.yml index 1925b5f2c..742b46712 100644 --- a/.travis.yml +++ b/.travis.yml @@ -17,6 +17,7 @@ before_install: # Decrypt the credentials file and copy it over to the destination. - openssl aes-256-cbc -K $encrypted_ebb86cbccb5d_key -iv $encrypted_ebb86cbccb5d_iv -in credentials.tar.enc -out credentials.tar -d - tar xvf credentials.tar + - mv ./spine-dev.json ./testutil-gcloud/src/test/resources # Install the complete gcloud SDK to access the Datastore emulator. - ./scripts/install-gcloud.sh # Add the newly installed gcloud SDK to PATH overriding the default Travis version. diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java index 78cea9190..b994ddf8d 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java @@ -217,10 +217,10 @@ protected Iterable wrappers() { } /** - * Returs the instance of wrapped {@link Datastore}. + * Returns the instance of wrapped {@link Datastore}. */ @VisibleForTesting - protected Datastore datastore() { + public Datastore datastore() { return datastore; } diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java index bee38275c..1207e1492 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java @@ -199,7 +199,7 @@ public void createOrUpdate(Collection entities) { * @return the {@link Entity} or {@code null} in case of no results for the key given * @see DatastoreReader#get(Key) */ - public Entity read(Key key) { + public @Nullable Entity read(Key key) { return actor.get(key); } diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java index 98bd808a6..0e8d6f0dc 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java @@ -20,7 +20,9 @@ package io.spine.testing.server.storage.datastore; +import com.google.common.annotations.VisibleForTesting; import io.spine.server.storage.datastore.DatastoreWrapper; +import org.checkerframework.checker.nullness.qual.Nullable; import static com.google.common.base.Preconditions.checkNotNull; @@ -29,7 +31,7 @@ */ public final class SpyStorageFactory extends TestDatastoreStorageFactory { - private static DatastoreWrapper injectedWrapper = null; + private static @Nullable DatastoreWrapper injectedWrapper = null; /** * Injects a given {@code DatastoreWrapper} into the storage factory. @@ -39,6 +41,7 @@ public final class SpyStorageFactory extends TestDatastoreStorageFactory { *

Should be called before the {@code SpyStorageFactory} instance is created. */ public static void injectWrapper(DatastoreWrapper wrapper) { + checkNotNull(wrapper); injectedWrapper = wrapper; } @@ -50,4 +53,9 @@ public SpyStorageFactory() { protected DatastoreWrapper createDatastoreWrapper(boolean multitenant) { return injectedWrapper; } + + @VisibleForTesting + static void clearInjectedWrapper() { + injectedWrapper = null; + } } diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java index fdf96a754..ba814493b 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java @@ -21,12 +21,18 @@ package io.spine.testing.server.storage.datastore; import com.google.cloud.datastore.Datastore; +import com.google.common.collect.ImmutableSet; import com.google.common.flogger.FluentLogger; import io.spine.annotation.Internal; import io.spine.server.storage.datastore.DatastoreStorageFactory; import io.spine.server.storage.datastore.DatastoreWrapper; import io.spine.server.storage.datastore.type.DatastoreTypeRegistryFactory; +import java.util.Collection; +import java.util.HashSet; + +import static com.google.common.base.Preconditions.checkNotNull; + /** * A test implementation of the {@link DatastoreStorageFactory}. * @@ -37,6 +43,8 @@ public class TestDatastoreStorageFactory extends DatastoreStorageFactory { private static final FluentLogger logger = FluentLogger.forEnclosingClass(); + private final Collection allCreatedWrappers = new HashSet<>(); + protected TestDatastoreStorageFactory(Datastore datastore) { super(DatastoreStorageFactory .newBuilder() @@ -58,13 +66,21 @@ public static TestDatastoreStorageFactory local() { * Creates a new factory instance which wraps the given Datastore. */ public static TestDatastoreStorageFactory basedOn(Datastore datastore) { + checkNotNull(datastore); return new TestDatastoreStorageFactory(datastore); } @Internal @Override protected DatastoreWrapper createDatastoreWrapper(boolean multitenant) { - return TestDatastoreWrapper.wrap(datastore(), false); + TestDatastoreWrapper wrapper = TestDatastoreWrapper.wrap(datastore(), false); + allCreatedWrappers.add(wrapper); + return wrapper; + } + + @Override + protected Iterable wrappers() { + return ImmutableSet.copyOf(allCreatedWrappers); } /** diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java index a1660604e..c2a34231e 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java @@ -26,6 +26,7 @@ import com.google.cloud.datastore.KeyFactory; import com.google.cloud.datastore.Query; import com.google.cloud.datastore.StructuredQuery; +import com.google.common.annotations.VisibleForTesting; import io.spine.server.storage.datastore.DatastoreWrapper; import io.spine.server.storage.datastore.Kind; import io.spine.server.storage.datastore.tenant.NamespaceSupplier; @@ -34,6 +35,7 @@ import java.util.Collection; import java.util.List; +import static com.google.common.base.Preconditions.checkNotNull; import static com.google.common.collect.Lists.newArrayList; import static io.spine.util.Exceptions.newIllegalStateException; @@ -76,10 +78,11 @@ protected TestDatastoreWrapper(Datastore datastore, boolean waitForConsistency) *

The {@code waitForConsistency} parameter allows to add a delay to each write operation to * compensate for the eventual consistency of the storage. * - *

The {@code waitForConsistency} parameter should be set to {@code false} when wrapping a - * local Datastore emulator. + *

The {@code waitForConsistency} parameter should usually be set to {@code false} when + * working with a local Datastore emulator. */ public static TestDatastoreWrapper wrap(Datastore datastore, boolean waitForConsistency) { + checkNotNull(datastore); return new TestDatastoreWrapper(datastore, waitForConsistency); } @@ -153,7 +156,6 @@ private void dropTableConsistently(String table) { } } - @SuppressWarnings("BusyWait") // allow Datastore to become consistent before reading. private void waitForConsistency() { if (!waitForConsistency) { _debug().log("Wait for consistency is not required."); @@ -161,6 +163,12 @@ private void waitForConsistency() { } _debug().log("Waiting for data consistency to establish."); + doWaitForConsistency(); + } + + @SuppressWarnings("BusyWait") // allow Datastore to become consistent before reading. + @VisibleForTesting + protected void doWaitForConsistency() { for (int awaitCycle = 0; awaitCycle < CONSISTENCY_AWAIT_ITERATIONS; awaitCycle++) { try { Thread.sleep(CONSISTENCY_AWAIT_TIME_MS); diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index 4818872f2..15b748b22 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -25,6 +25,7 @@ import com.google.cloud.NoCredentials; import com.google.cloud.datastore.Datastore; import com.google.cloud.datastore.DatastoreOptions; +import com.google.common.annotations.VisibleForTesting; import io.spine.io.Resource; import io.spine.logging.Logging; import io.spine.server.storage.datastore.ProjectId; @@ -33,6 +34,7 @@ import java.io.InputStream; import static com.google.auth.oauth2.ServiceAccountCredentials.fromStream; +import static com.google.common.base.Preconditions.checkNotNull; import static io.spine.io.Resource.file; import static io.spine.util.Exceptions.newIllegalArgumentException; import static java.lang.String.format; @@ -48,7 +50,8 @@ public final class TestDatastores implements Logging { *

See * {@code gcloud} docs. */ - private static final int DEFAULT_EMULATOR_PORT = 8081; + @VisibleForTesting + static final int DEFAULT_EMULATOR_PORT = 8081; private static final String LOCALHOST = "localhost"; /** @@ -72,15 +75,8 @@ public static Datastore local() { * Creates a {@link Datastore} connected to the local Datastore emulator at the specified port. */ public static Datastore local(int port) { - String address = format("%s:%s", LOCALHOST, port); - return local(address); - } + String address = format("%s:%d", LOCALHOST, port); - /** - * Creates a {@link Datastore} connected to the local Datastore emulator at the specified - * address. - */ - public static Datastore local(String address) { DatastoreOptions options = DatastoreOptions .newBuilder() .setProjectId(LOCAL_PROJECT_ID.value()) @@ -99,6 +95,7 @@ public static Datastore local(String address) { * classpath. */ public static Datastore remote(String serviceAccountPath) { + checkNotNull(serviceAccountPath); return remote(file(serviceAccountPath)); } @@ -107,6 +104,7 @@ public static Datastore remote(String serviceAccountPath) { * given service account resource. */ public static Datastore remote(Resource serviceAccount) { + checkNotNull(serviceAccount); try { Credentials credentials = credentialsFrom(serviceAccount); DatastoreOptions options = DatastoreOptions diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/SpyStorageFactoryTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/SpyStorageFactoryTest.java new file mode 100644 index 000000000..75e7d1bc8 --- /dev/null +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/SpyStorageFactoryTest.java @@ -0,0 +1,61 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.testing.server.storage.datastore; + +import com.google.cloud.datastore.Datastore; +import com.google.common.testing.NullPointerTester; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +import static com.google.common.truth.Truth.assertThat; +import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; +import static org.junit.jupiter.api.Assertions.assertThrows; + +@DisplayName("`SpyStorageFactory` should") +class SpyStorageFactoryTest { + + @Test + @DisplayName(NOT_ACCEPT_NULLS) + void passNullToleranceCheck() { + new NullPointerTester() + .testAllPublicStaticMethods(SpyStorageFactory.class); + } + + @Test + @DisplayName("inject a given `DatastoreWrapper`") + void injectDatastoreWrapper() { + Datastore datastore = TestDatastores.local(); + TestDatastoreWrapper wrapper = TestDatastoreWrapper.wrap(datastore, false); + SpyStorageFactory.injectWrapper(wrapper); + SpyStorageFactory factory = new SpyStorageFactory(); + Datastore datastoreFromFactory = factory.datastore(); + + assertThat(datastoreFromFactory) + .isSameInstanceAs(datastore); + } + + @Test + @DisplayName("throw `NPE` if being created while no wrapper was injected") + void throwWithoutWrapperInjected() { + SpyStorageFactory.clearInjectedWrapper(); + assertThrows(NullPointerException.class, SpyStorageFactory::new); + } +} diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactoryTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactoryTest.java new file mode 100644 index 000000000..bdb79090f --- /dev/null +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactoryTest.java @@ -0,0 +1,78 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.testing.server.storage.datastore; + +import com.google.cloud.datastore.Entity; +import com.google.cloud.datastore.Key; +import com.google.common.testing.NullPointerTester; +import io.spine.server.storage.datastore.DatastoreWrapper; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +import static com.google.common.truth.Truth.assertThat; +import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; +import static io.spine.testing.server.storage.datastore.given.AnEntity.withKeyCreatedBy; + +@DisplayName("`TestDatastoreStorageFactory` should") +class TestDatastoreStorageFactoryTest { + + @Test + @DisplayName(NOT_ACCEPT_NULLS) + void passNullToleranceCheck() { + new NullPointerTester() + .testAllPublicStaticMethods(TestDatastoreStorageFactory.class); + } + + @Test + @DisplayName("wrap the specified Datastore with a `TestDatastoreWrapper`") + void wrapDatastore() { + TestDatastoreStorageFactory factory = TestDatastoreStorageFactory.local(); + DatastoreWrapper wrapper = factory.createDatastoreWrapper(false); + assertThat(wrapper) + .isInstanceOf(TestDatastoreWrapper.class); + } + + @Test + @DisplayName("clear all data in the Datastore") + void clearDatastore() { + // Initialize the factory. + TestDatastoreStorageFactory factory = TestDatastoreStorageFactory.local(); + DatastoreWrapper wrapper = factory.createDatastoreWrapper(false); + + // Create an entity. + Entity entity = withKeyCreatedBy(wrapper); + Key key = entity.getKey(); + wrapper.createOrUpdate(entity); + + // Make sure the entity is read from the Datastore by key. + Entity entityReadBeforeClear = wrapper.read(key); + assertThat(entityReadBeforeClear) + .isNotNull(); + + // Clear the Datastore. + factory.clear(); + + // Make sure entity is no longer present. + Entity entityReadAfterClear = wrapper.read(key); + assertThat(entityReadAfterClear) + .isNull(); + } +} diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapperTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapperTest.java new file mode 100644 index 000000000..c79b9424a --- /dev/null +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapperTest.java @@ -0,0 +1,91 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.testing.server.storage.datastore; + +import com.google.cloud.datastore.Entity; +import com.google.cloud.datastore.Key; +import com.google.common.testing.NullPointerTester; +import io.spine.testing.server.storage.datastore.given.ATestDatastoreWrapper; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +import static com.google.common.truth.Truth.assertThat; +import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; +import static io.spine.testing.server.storage.datastore.given.ATestDatastoreWrapper.wrap; +import static io.spine.testing.server.storage.datastore.given.AnEntity.withKeyCreatedBy; + +@DisplayName("`TestDatastoreWrapper` should") +class TestDatastoreWrapperTest { + + @Test + @DisplayName(NOT_ACCEPT_NULLS) + void passNullToleranceCheck() { + new NullPointerTester() + .testAllPublicStaticMethods(TestDatastoreWrapper.class); + } + + @Test + @DisplayName("wait for consistency if the parameter is specified on creation") + void waitForConsistency() { + ATestDatastoreWrapper wrapper = wrap(TestDatastores.local(), true); + Entity entity = withKeyCreatedBy(wrapper); + wrapper.createOrUpdate(entity); + + assertThat(wrapper.waitedForConsistency()) + .isTrue(); + } + + @Test + @DisplayName("ignore the wait for consistency if the parameter was set to `false`") + void notWaitForConsistency() { + ATestDatastoreWrapper wrapper = wrap(TestDatastores.local(), false); + Entity entity = withKeyCreatedBy(wrapper); + wrapper.createOrUpdate(entity); + + assertThat(wrapper.waitedForConsistency()) + .isFalse(); + } + + @Test + @DisplayName("drop all tables in the Datastore") + void dropAllTables() { + // Initialize the wrapper. + TestDatastoreWrapper wrapper = TestDatastoreWrapper.wrap(TestDatastores.local(), false); + + // Create an entity. + Entity entity = withKeyCreatedBy(wrapper); + Key key = entity.getKey(); + wrapper.createOrUpdate(entity); + + // Make sure the entity is read from the Datastore by key. + Entity entityReadBeforeClear = wrapper.read(key); + assertThat(entityReadBeforeClear) + .isNotNull(); + + // Drop all data. + wrapper.dropAllTables(); + + // Make sure the entity is no longer present in the Datastore. + Entity entityReadAfterClear = wrapper.read(key); + assertThat(entityReadAfterClear) + .isNull(); + } +} diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java new file mode 100644 index 000000000..7e9a1fc07 --- /dev/null +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java @@ -0,0 +1,99 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.testing.server.storage.datastore; + +import com.google.cloud.datastore.Datastore; +import io.spine.io.Resource; +import io.spine.testing.UtilityClassTest; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +import static com.google.common.truth.Truth.assertThat; +import static io.spine.testing.server.storage.datastore.TestDatastores.DEFAULT_EMULATOR_PORT; +import static java.lang.String.format; + +@DisplayName("`TestDatastores` utility should") +class TestDatastoresTest extends UtilityClassTest { + + TestDatastoresTest() { + super(TestDatastores.class); + } + + @Nested + @DisplayName("create a `Datastore` connected to the local Datastore emulator running at") + class CreateLocalDatastore { + + private static final String ADDRESS_FORMAT = "localhost:%d"; + + @Test + @DisplayName("the default emulator address") + void atDefaultAddress() { + Datastore datastore = TestDatastores.local(); + String host = datastore.getOptions() + .getHost(); + String expectedHost = format(ADDRESS_FORMAT, DEFAULT_EMULATOR_PORT); + assertThat(host) + .isEqualTo(expectedHost); + } + + @Test + @DisplayName("a custom port") + void atCustomPort() { + int port = 8080; + Datastore datastore = TestDatastores.local(port); + String host = datastore.getOptions() + .getHost(); + String expectedHost = format(ADDRESS_FORMAT, port); + assertThat(host) + .isEqualTo(expectedHost); + } + } + + @Nested + @DisplayName("create a `Datastore` connected to the remote Datastore described by") + class CreateRemoteDatastore { + + private static final String SPINE_DEV_JSON = "spine-dev.json"; + private static final String PROJECT_ID = "spine-dev"; + + @Test + @DisplayName("the service account resource at path") + void byResourceAtPath() { + Datastore datastore = TestDatastores.remote(SPINE_DEV_JSON); + String projectId = datastore.getOptions() + .getProjectId(); + assertThat(projectId) + .isEqualTo(PROJECT_ID); + } + + @Test + @DisplayName("the service account resource") + void byResource() { + Resource serviceAccount = Resource.file(SPINE_DEV_JSON); + Datastore datastore = TestDatastores.remote(serviceAccount); + String projectId = datastore.getOptions() + .getProjectId(); + assertThat(projectId) + .isEqualTo(PROJECT_ID); + } + } +} diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/ATestDatastoreWrapper.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/ATestDatastoreWrapper.java new file mode 100644 index 000000000..360f281f5 --- /dev/null +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/ATestDatastoreWrapper.java @@ -0,0 +1,47 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.testing.server.storage.datastore.given; + +import com.google.cloud.datastore.Datastore; +import io.spine.testing.server.storage.datastore.TestDatastoreWrapper; + +public final class ATestDatastoreWrapper extends TestDatastoreWrapper { + + private boolean waitedForConsistency; + + private ATestDatastoreWrapper(Datastore datastore, boolean waitForConsistency) { + super(datastore, waitForConsistency); + } + + public static ATestDatastoreWrapper wrap(Datastore datastore, boolean waitForConsistency) { + return new ATestDatastoreWrapper(datastore, waitForConsistency); + } + + @Override + protected void doWaitForConsistency() { + super.doWaitForConsistency(); + waitedForConsistency = true; + } + + public boolean waitedForConsistency() { + return waitedForConsistency; + } +} diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/AnEntity.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/AnEntity.java new file mode 100644 index 000000000..5fce1e72c --- /dev/null +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/AnEntity.java @@ -0,0 +1,55 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.testing.server.storage.datastore.given; + +import com.google.cloud.datastore.Entity; +import com.google.cloud.datastore.Key; +import com.google.cloud.datastore.KeyFactory; +import io.spine.server.storage.datastore.DatastoreWrapper; +import io.spine.server.storage.datastore.Kind; + +public final class AnEntity { + + private static final Kind ENTITY_KIND = Kind.of("the-entity-kind"); + + /** Prevents instantiation of this test env class. */ + private AnEntity() { + } + + public static Entity withKeyCreatedBy(DatastoreWrapper wrapper) { + Key key = keyCreatedBy(wrapper); + Entity entity = withKey(key); + return entity; + } + + private static Entity withKey(Key key) { + Entity entity = Entity.newBuilder(key) + .build(); + return entity; + } + + private static Key keyCreatedBy(DatastoreWrapper wrapper) { + KeyFactory keyFactory = wrapper.keyFactory(ENTITY_KIND); + int someId = 151; + Key key = keyFactory.newKey(someId); + return key; + } +} diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/package-info.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/package-info.java new file mode 100644 index 000000000..a5a1c50d7 --- /dev/null +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/given/package-info.java @@ -0,0 +1,31 @@ +/* + * Copyright 2019, TeamDev. All rights reserved. + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/** + * This package contains the test env classes for the `testutil-gcloud` module. + */ + +@CheckReturnValue +@ParametersAreNonnullByDefault +package io.spine.testing.server.storage.datastore.given; + +import com.google.errorprone.annotations.CheckReturnValue; + +import javax.annotation.ParametersAreNonnullByDefault; From 421a96d787d437bf2113b033762d9eafc3558e7c Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 21:00:15 +0300 Subject: [PATCH 12/30] Update `config` --- config | 2 +- license-report.md | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/config b/config index dbb44338d..6a07e48f8 160000 --- a/config +++ b/config @@ -1 +1 @@ -Subproject commit dbb44338da3564cfa75a31a021a074aee3b62d00 +Subproject commit 6a07e48f83113e89198f75462a76911e74546152 diff --git a/license-report.md b/license-report.md index 2264832c6..33649311c 100644 --- a/license-report.md +++ b/license-report.md @@ -734,7 +734,7 @@ The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 19:17:26 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 20:53:35 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -1474,7 +1474,7 @@ This report was generated on **Tue Oct 01 19:17:26 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 19:17:38 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 20:53:49 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -2234,4 +2234,4 @@ This report was generated on **Tue Oct 01 19:17:38 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 19:17:51 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file +This report was generated on **Tue Oct 01 20:54:02 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file From 39a7d6a9cc44ed52c6dd9f1f93b25a415daa7518 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 21:08:44 +0300 Subject: [PATCH 13/30] Update Spine version to `1.1.3-SNAPSHOT+1` --- README.md | 7 +++++-- version.gradle | 4 ++-- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 8e4f692c9..1156f01ab 100644 --- a/README.md +++ b/README.md @@ -14,10 +14,13 @@ dependencies { implementation ( // Datastore Storage support library. - "io.spine.gcloud:spine-datastore:1.1.2", + "io.spine.gcloud:spine-datastore:1.1.3-SNAPSHOT+1", // Stackdriver Trace support library. - "io.spine.gcloud:spine-stackdriver-trace:1.1.2" + "io.spine.gcloud:spine-stackdriver-trace:1.1.3-SNAPSHOT+1", + + // Datastore-related test utilities (if needed). + "io.spine.gcloud:testutil-gcloud:1.1.3-SNAPSHOT+1" ) } ``` diff --git a/version.gradle b/version.gradle index faacd50cb..4f15fcc23 100644 --- a/version.gradle +++ b/version.gradle @@ -25,13 +25,13 @@ * {@code .config/gradle/dependencies.gradle}. */ -def final SPINE_VERSION = '1.1.2' +def final SPINE_VERSION = '1.1.3-SNAPSHOT+1' ext { versionToPublish = SPINE_VERSION spineBaseVersion = SPINE_VERSION - spineCoreVersion = SPINE_VERSION + spineCoreVersion = '1.1.2' datastoreVersion = '1.91.0' } From a8fa4a8568aa507158cbae6ac7b109526d1d716f Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 21:08:51 +0300 Subject: [PATCH 14/30] Fix build on Travis --- .travis.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.travis.yml b/.travis.yml index 742b46712..d2914dba4 100644 --- a/.travis.yml +++ b/.travis.yml @@ -17,6 +17,7 @@ before_install: # Decrypt the credentials file and copy it over to the destination. - openssl aes-256-cbc -K $encrypted_ebb86cbccb5d_key -iv $encrypted_ebb86cbccb5d_iv -in credentials.tar.enc -out credentials.tar -d - tar xvf credentials.tar + - mkdir ./testutil-gcloud/src/test/resources - mv ./spine-dev.json ./testutil-gcloud/src/test/resources # Install the complete gcloud SDK to access the Datastore emulator. - ./scripts/install-gcloud.sh From 3b28bcc03239093858634179fcbd06e009c32de4 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 21:12:39 +0300 Subject: [PATCH 15/30] Update license report and `pom.xml` --- license-report.md | 12 ++++++------ pom.xml | 6 +++--- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/license-report.md b/license-report.md index 33649311c..35c64b527 100644 --- a/license-report.md +++ b/license-report.md @@ -1,6 +1,6 @@ -# Dependencies of `io.spine.gcloud:spine-datastore:1.1.2` +# Dependencies of `io.spine.gcloud:spine-datastore:1.1.3-SNAPSHOT+1` ## Runtime 1. **Group:** com.fasterxml.jackson.core **Name:** jackson-core **Version:** 2.9.9 @@ -734,12 +734,12 @@ The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 20:53:35 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 21:07:36 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). -# Dependencies of `io.spine.gcloud:spine-stackdriver-trace:1.1.2` +# Dependencies of `io.spine.gcloud:spine-stackdriver-trace:1.1.3-SNAPSHOT+1` ## Runtime 1. **Group:** com.fasterxml.jackson.core **Name:** jackson-core **Version:** 2.9.6 @@ -1474,12 +1474,12 @@ This report was generated on **Tue Oct 01 20:53:35 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 20:53:49 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Tue Oct 01 21:07:49 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). -# Dependencies of `io.spine.gcloud:spine-testutil-gcloud:1.1.2` +# Dependencies of `io.spine.gcloud:spine-testutil-gcloud:1.1.3-SNAPSHOT+1` ## Runtime 1. **Group:** com.fasterxml.jackson.core **Name:** jackson-core **Version:** 2.9.9 @@ -2234,4 +2234,4 @@ This report was generated on **Tue Oct 01 20:53:49 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 20:54:02 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file +This report was generated on **Tue Oct 01 21:08:02 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file diff --git a/pom.xml b/pom.xml index ca0d06f82..d1d3883cc 100644 --- a/pom.xml +++ b/pom.xml @@ -12,7 +12,7 @@ all modules and does not describe the project structure per-subproject. io.spine.gcloud spine-gcloud-java -1.1.2 +1.1.3-SNAPSHOT+1 2015 @@ -114,12 +114,12 @@ all modules and does not describe the project structure per-subproject. io.spine.tools spine-errorprone-checks - 1.1.2 + 1.1.3-SNAPSHOT+1 io.spine.tools spine-protoc-plugin - 1.1.2 + 1.1.3-SNAPSHOT+1 net.sourceforge.pmd From 4a18b934a69f03ed802b818315366d44d36976f5 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 21:14:46 +0300 Subject: [PATCH 16/30] Fix build on Travis --- .travis.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.travis.yml b/.travis.yml index d2914dba4..afc1d0db5 100644 --- a/.travis.yml +++ b/.travis.yml @@ -19,6 +19,8 @@ before_install: - tar xvf credentials.tar - mkdir ./testutil-gcloud/src/test/resources - mv ./spine-dev.json ./testutil-gcloud/src/test/resources + - mkdir ./datastore/src/test/resources + - mv ./spine-dev.json ./datastore/src/test/resources # Install the complete gcloud SDK to access the Datastore emulator. - ./scripts/install-gcloud.sh # Add the newly installed gcloud SDK to PATH overriding the default Travis version. From 72636202a3b4738988f444bf1dc669fafcda1eec Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 21:19:50 +0300 Subject: [PATCH 17/30] Add missing `VisibleForTesting` annotations --- .../io/spine/server/storage/datastore/DatastoreWrapper.java | 2 ++ 1 file changed, 2 insertions(+) diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java index 1207e1492..4fda458ad 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreWrapper.java @@ -387,6 +387,7 @@ public void delete(Key... keys) { * @param table * kind (a.k.a. type, table, etc.) of the records to delete */ + @VisibleForTesting protected void dropTable(String table) { Namespace namespace = currentNamespace(); StructuredQuery query = @@ -399,6 +400,7 @@ protected void dropTable(String table) { deleteEntities(entities); } + @VisibleForTesting protected void deleteEntities(Collection entities) { List keyList = entities.stream() From bdc8358e364dccedc0a63eaad5efaf858a6141bc Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 21:24:34 +0300 Subject: [PATCH 18/30] Fix build on Travis --- .travis.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index afc1d0db5..0ec14f396 100644 --- a/.travis.yml +++ b/.travis.yml @@ -18,9 +18,9 @@ before_install: - openssl aes-256-cbc -K $encrypted_ebb86cbccb5d_key -iv $encrypted_ebb86cbccb5d_iv -in credentials.tar.enc -out credentials.tar -d - tar xvf credentials.tar - mkdir ./testutil-gcloud/src/test/resources - - mv ./spine-dev.json ./testutil-gcloud/src/test/resources + - cp ./spine-dev.json ./testutil-gcloud/src/test/resources/spine-dev.json - mkdir ./datastore/src/test/resources - - mv ./spine-dev.json ./datastore/src/test/resources + - cp ./spine-dev.json ./datastore/src/test/resources/spine-dev.json # Install the complete gcloud SDK to access the Datastore emulator. - ./scripts/install-gcloud.sh # Add the newly installed gcloud SDK to PATH overriding the default Travis version. From 12816b3f565416c3847b3e986b81501c2cf357bb Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Tue, 1 Oct 2019 21:24:50 +0300 Subject: [PATCH 19/30] Fix naming and docs Also did a minor test refactoring. --- .../storage/datastore/given/DatastoreWrapperTestEnv.java | 4 ++-- .../storage/datastore/tenant/NamespaceConvertersTest.java | 7 ++++++- .../storage/datastore/TestDatastoreStorageFactory.java | 2 +- 3 files changed, 9 insertions(+), 4 deletions(-) diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java b/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java index 2f0a39790..f63a8361e 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/given/DatastoreWrapperTestEnv.java @@ -40,7 +40,7 @@ public class DatastoreWrapperTestEnv { public static final String NAMESPACE_HOLDER_KIND = "spine.test.NAMESPACE_HOLDER_KIND"; public static final Kind GENERIC_ENTITY_KIND = Kind.of("my.entity"); - private static final String SERVICE_ACCOUNT_FILE_PATH = "spine-dev.json"; + private static final String SERVICE_ACCOUNT_RESOURCE_PATH = "spine-dev.json"; /** * Prevents instantiation of this test environment. @@ -73,6 +73,6 @@ public static Datastore localDatastore() { } public static Datastore remoteDatastore() { - return TestDatastores.remote(SERVICE_ACCOUNT_FILE_PATH); + return TestDatastores.remote(SERVICE_ACCOUNT_RESOURCE_PATH); } } diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceConvertersTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceConvertersTest.java index 3525e0f06..3a31c5a6e 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceConvertersTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceConvertersTest.java @@ -21,6 +21,7 @@ package io.spine.server.storage.datastore.tenant; import io.spine.core.TenantId; +import io.spine.testing.UtilityClassTest; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; @@ -29,7 +30,11 @@ import static org.junit.jupiter.api.Assertions.assertEquals; @DisplayName("`NamespaceConverters` should") -class NamespaceConvertersTest { +class NamespaceConvertersTest extends UtilityClassTest { + + NamespaceConvertersTest() { + super(NamespaceConverters.class); + } @Test @DisplayName(HAVE_PARAMETERLESS_CTOR) diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java index ba814493b..6799efca1 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactory.java @@ -95,7 +95,7 @@ public void setUp() { /** * Clears all data in the local Datastore. * - *

Is effectively the same as {@link #clear()}. + *

May be effectively the same as {@link #clear()}. * *

NOTE: does not stop the server but just deletes all records. * From c0f37660d818eaa74288b4b827f693144acdd0cd Mon Sep 17 00:00:00 2001 From: Dima Kuzmin Date: Wed, 2 Oct 2019 01:40:59 +0300 Subject: [PATCH 20/30] Add ability to specify custom project ID for the local datastore Also fixed the project ID in `start-datastore scripts. --- .../DatastoreStorageFactoryBuilderTest.java | 4 ++-- .../DatastoreStorageFactoryTest.java | 4 ++-- .../datastore/tenant/NamespaceTest.java | 4 ++-- .../datastore/type/DsColumnTypesTest.java | 4 ++-- scripts/start-datastore.bat | 2 +- scripts/start-datastore.sh | 2 +- .../storage/datastore/TestDatastores.java | 17 ++++++++++----- .../storage/datastore/TestDatastoresTest.java | 21 +++++++++++++++++++ 8 files changed, 43 insertions(+), 15 deletions(-) diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java index 0ac46c471..19d4594bd 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryBuilderTest.java @@ -40,7 +40,7 @@ import static io.spine.testing.DisplayNames.HAVE_PARAMETERLESS_CTOR; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; import static io.spine.testing.Tests.assertHasPrivateParameterlessCtor; -import static io.spine.testing.server.storage.datastore.TestDatastores.localProjectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.defaultLocalProjectId; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertThrows; @@ -102,7 +102,7 @@ class Namespaces { void setUp() { builder = DatastoreOptions .newBuilder() - .setProjectId(localProjectId().getValue()); + .setProjectId(defaultLocalProjectId().getValue()); } @Test diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java index b84bde0a6..e72af9276 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/DatastoreStorageFactoryTest.java @@ -47,7 +47,7 @@ import static io.spine.server.tenant.TenantAwareRunner.with; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; import static io.spine.testing.server.storage.datastore.TestDatastores.local; -import static io.spine.testing.server.storage.datastore.TestDatastores.localProjectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.defaultLocalProjectId; import static org.junit.jupiter.api.Assertions.assertNotEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertSame; @@ -177,7 +177,7 @@ private static Key.Builder whiteForTenant(DsPropertyStorage storage, TenantId te with(tenant).run( () -> storage.write(recordId, message) ); - return Key.newBuilder(localProjectId().getValue(), + return Key.newBuilder(defaultLocalProjectId().getValue(), TypeName.of(message) .value(), recordId.getValue()); diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java index ce3dade86..f865a0da2 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/tenant/NamespaceTest.java @@ -31,7 +31,7 @@ import org.junit.jupiter.api.Test; import static io.spine.testing.DisplayNames.NOT_ACCEPT_NULLS; -import static io.spine.testing.server.storage.datastore.TestDatastores.localProjectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.defaultLocalProjectId; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; @@ -44,7 +44,7 @@ class NamespaceTest { @Test @DisplayName(NOT_ACCEPT_NULLS) void testNulls() { - ProjectId defaultProjectId = localProjectId(); + ProjectId defaultProjectId = defaultLocalProjectId(); Key defaultKey = Key.newBuilder(defaultProjectId.getValue(), "kind", "name") .build(); new NullPointerTester() diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java index 8657656bb..518f63d04 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/type/DsColumnTypesTest.java @@ -40,7 +40,7 @@ import static io.spine.server.storage.datastore.type.DsColumnTypes.timestampType; import static io.spine.testing.DisplayNames.HAVE_PARAMETERLESS_CTOR; import static io.spine.testing.Tests.assertHasPrivateParameterlessCtor; -import static io.spine.testing.server.storage.datastore.TestDatastores.localProjectId; +import static io.spine.testing.server.storage.datastore.TestDatastores.defaultLocalProjectId; @DisplayName("DsColumnTypes should") class DsColumnTypesTest { @@ -225,7 +225,7 @@ private void setDatastoreType(DatastoreColumnType type, } private static BaseEntity.Builder entityBuilder() { - String projectId = localProjectId().value(); + String projectId = defaultLocalProjectId().value(); Key key = Key.newBuilder(projectId, "some-entity-kind", "some-name") .build(); Entity.Builder builder = Entity.newBuilder(key); diff --git a/scripts/start-datastore.bat b/scripts/start-datastore.bat index 9e8e9130e..f4bf0957f 100644 --- a/scripts/start-datastore.bat +++ b/scripts/start-datastore.bat @@ -1 +1 @@ -gcloud beta emulators datastore start --project=spine-dev --consistency 1.0 --no-store-on-disk +gcloud beta emulators datastore start --project=test-project --consistency 1.0 --no-store-on-disk diff --git a/scripts/start-datastore.sh b/scripts/start-datastore.sh index 9e8e9130e..f4bf0957f 100755 --- a/scripts/start-datastore.sh +++ b/scripts/start-datastore.sh @@ -1 +1 @@ -gcloud beta emulators datastore start --project=spine-dev --consistency 1.0 --no-store-on-disk +gcloud beta emulators datastore start --project=test-project --consistency 1.0 --no-store-on-disk diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index 15b748b22..9141a3cf9 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -57,7 +57,7 @@ public final class TestDatastores implements Logging { /** * The project ID which is used when running on local Datastore emulator. */ - private static final ProjectId LOCAL_PROJECT_ID = ProjectId.of("test-project"); + private static final ProjectId DEFAULT_LOCAL_PROJECT_ID = ProjectId.of("test-project"); /** Prevents instantiation of this utility class. */ private TestDatastores() { @@ -75,11 +75,18 @@ public static Datastore local() { * Creates a {@link Datastore} connected to the local Datastore emulator at the specified port. */ public static Datastore local(int port) { - String address = format("%s:%d", LOCALHOST, port); + return local(DEFAULT_LOCAL_PROJECT_ID, port); + } + /** + * Creates a {@link Datastore} connected to the local Datastore emulator at the specified port + * which runs with the specified project ID. + */ + public static Datastore local(ProjectId projectId, int port) { + String address = format("%s:%d", LOCALHOST, port); DatastoreOptions options = DatastoreOptions .newBuilder() - .setProjectId(LOCAL_PROJECT_ID.value()) + .setProjectId(projectId.value()) .setHost(address) .setCredentials(NoCredentials.getInstance()) .build(); @@ -125,7 +132,7 @@ private static Credentials credentialsFrom(Resource serviceAccount) throws IOExc return credentials; } - public static ProjectId localProjectId() { - return LOCAL_PROJECT_ID; + public static ProjectId defaultLocalProjectId() { + return DEFAULT_LOCAL_PROJECT_ID; } } diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java index 7e9a1fc07..0d1840bb5 100644 --- a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java @@ -21,7 +21,9 @@ package io.spine.testing.server.storage.datastore; import com.google.cloud.datastore.Datastore; +import com.google.cloud.datastore.DatastoreOptions; import io.spine.io.Resource; +import io.spine.server.storage.datastore.ProjectId; import io.spine.testing.UtilityClassTest; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Nested; @@ -66,6 +68,25 @@ void atCustomPort() { assertThat(host) .isEqualTo(expectedHost); } + + @Test + @DisplayName("a custom port with a custom project ID") + void atCustomPortWithCustomId() { + int port = 8080; + String id = "the-test-project"; + ProjectId projectId = ProjectId.of(id); + Datastore datastore = TestDatastores.local(projectId, port); + + DatastoreOptions options = datastore.getOptions(); + String host = options.getHost(); + String expectedHost = format(ADDRESS_FORMAT, port); + assertThat(host) + .isEqualTo(expectedHost); + + String actualProjectId = options.getProjectId(); + assertThat(actualProjectId) + .isEqualTo(id); + } } @Nested From aa2a4a6c0aafcd2ee8d2c52b0e7fc92ab9b97c9a Mon Sep 17 00:00:00 2001 From: Dima Kuzmin Date: Wed, 2 Oct 2019 01:42:42 +0300 Subject: [PATCH 21/30] Fix redundant method visibility --- .../server/storage/datastore/DatastoreStorageFactory.java | 2 +- .../server/storage/datastore/SpyStorageFactory.java | 7 +++++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java index b994ddf8d..e5b31ea71 100644 --- a/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java +++ b/datastore/src/main/java/io/spine/server/storage/datastore/DatastoreStorageFactory.java @@ -220,7 +220,7 @@ protected Iterable wrappers() { * Returns the instance of wrapped {@link Datastore}. */ @VisibleForTesting - public Datastore datastore() { + protected Datastore datastore() { return datastore; } diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java index 0e8d6f0dc..0d6b13145 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/SpyStorageFactory.java @@ -20,6 +20,7 @@ package io.spine.testing.server.storage.datastore; +import com.google.cloud.datastore.Datastore; import com.google.common.annotations.VisibleForTesting; import io.spine.server.storage.datastore.DatastoreWrapper; import org.checkerframework.checker.nullness.qual.Nullable; @@ -58,4 +59,10 @@ protected DatastoreWrapper createDatastoreWrapper(boolean multitenant) { static void clearInjectedWrapper() { injectedWrapper = null; } + + @VisibleForTesting + @Override + protected Datastore datastore() { + return super.datastore(); + } } From 12ef2b9e7bb1ab6cd5d17942ff1e3d5b3e96fecb Mon Sep 17 00:00:00 2001 From: Dima Kuzmin Date: Wed, 2 Oct 2019 01:46:52 +0300 Subject: [PATCH 22/30] Fix unintended change --- .../java/io/spine/server/storage/datastore/ProjectIdTest.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/datastore/src/test/java/io/spine/server/storage/datastore/ProjectIdTest.java b/datastore/src/test/java/io/spine/server/storage/datastore/ProjectIdTest.java index 5d7682a95..fabaa8ed2 100644 --- a/datastore/src/test/java/io/spine/server/storage/datastore/ProjectIdTest.java +++ b/datastore/src/test/java/io/spine/server/storage/datastore/ProjectIdTest.java @@ -24,6 +24,7 @@ import com.google.cloud.datastore.DatastoreOptions; import com.google.common.testing.EqualsTester; import com.google.common.testing.NullPointerTester; +import io.spine.testing.server.storage.datastore.TestDatastores; import org.junit.jupiter.api.DisplayName; import org.junit.jupiter.api.Test; @@ -38,7 +39,7 @@ class ProjectIdTest { @DisplayName(NOT_ACCEPT_NULLS) void testNulls() { new NullPointerTester() - .setDefault(Datastore.class, local()) + .setDefault(Datastore.class, TestDatastores.local()) .testStaticMethods(ProjectId.class, NullPointerTester.Visibility.PACKAGE); } From 02f02c3c03d6ddc7a181cb4328327bbda4ceaaa2 Mon Sep 17 00:00:00 2001 From: Dima Kuzmin Date: Wed, 2 Oct 2019 01:53:17 +0300 Subject: [PATCH 23/30] Improve doc of default local project ID --- .../testing/server/storage/datastore/TestDatastores.java | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index 9141a3cf9..e2ca0095d 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -55,7 +55,13 @@ public final class TestDatastores implements Logging { private static final String LOCALHOST = "localhost"; /** - * The project ID which is used when running on local Datastore emulator. + * The default project ID to use when running on a local Datastore emulator. + * + *

For most tests, it's okay to use this ID even if some other project ID was passed to the + * emulator via the {@code --project} switch. + * + *

If, for some reason, you need to specify a custom project ID, please use + * {@link #local(ProjectId, int)}. */ private static final ProjectId DEFAULT_LOCAL_PROJECT_ID = ProjectId.of("test-project"); From 3f73ab26b3400af2333eb0ee9bba1ab21701e26d Mon Sep 17 00:00:00 2001 From: Dima Kuzmin Date: Wed, 2 Oct 2019 01:55:56 +0300 Subject: [PATCH 24/30] Fix grammar --- .../testing/server/storage/datastore/TestDatastoreWrapper.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java index c2a34231e..49b840334 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapper.java @@ -119,7 +119,7 @@ protected void dropTable(String table) { } } - @SuppressWarnings("BusyWait") // allow Datastore some time between cleanup attempts. + @SuppressWarnings("BusyWait") // allows Datastore some time between cleanup attempts. private void dropTableConsistently(String table) { Integer remainingEntityCount = null; int cleanupAttempts = 0; From 42736636e73647cd9aa229172b438de0556065ff Mon Sep 17 00:00:00 2001 From: Dima Kuzmin Date: Wed, 2 Oct 2019 01:57:02 +0300 Subject: [PATCH 25/30] Fix package info --- .../spine/testing/server/storage/datastore/package-info.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/package-info.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/package-info.java index f6830d6d3..7f61b24ca 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/package-info.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/package-info.java @@ -19,7 +19,8 @@ */ /** - * This package contains the testing utils for the Google Cloud Datastore storage implementation. + * This package contains the testing utils for the Google Cloud Datastore-based storage + * implementation. */ @CheckReturnValue From 56ebb062a6d2ab8f92219de14057747f43a755cd Mon Sep 17 00:00:00 2001 From: Dima Kuzmin Date: Wed, 2 Oct 2019 02:17:16 +0300 Subject: [PATCH 26/30] Throw an `IllegalStateException` on issues with reading service account To conform with the type already thrown by the `Resource`. --- .../testing/server/storage/datastore/TestDatastores.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index e2ca0095d..154c3a0cf 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -36,7 +36,7 @@ import static com.google.auth.oauth2.ServiceAccountCredentials.fromStream; import static com.google.common.base.Preconditions.checkNotNull; import static io.spine.io.Resource.file; -import static io.spine.util.Exceptions.newIllegalArgumentException; +import static io.spine.util.Exceptions.newIllegalStateException; import static java.lang.String.format; /** @@ -127,7 +127,7 @@ public static Datastore remote(Resource serviceAccount) { Datastore datastore = options.getService(); return datastore; } catch (IOException e) { - throw newIllegalArgumentException( + throw newIllegalStateException( e, "Cannot find the credentials file `%s`.", serviceAccount); } } From 7ec673bc83551e4e189222644a9f065d4bf7afda Mon Sep 17 00:00:00 2001 From: Dima Kuzmin Date: Wed, 2 Oct 2019 02:29:15 +0300 Subject: [PATCH 27/30] Add a test for problematic parsing of service account --- .travis.yml | 3 +-- .../testing/server/storage/datastore/TestDatastores.java | 2 +- .../server/storage/datastore/TestDatastoresTest.java | 8 ++++++++ testutil-gcloud/src/test/resources/random.json | 3 +++ 4 files changed, 13 insertions(+), 3 deletions(-) create mode 100644 testutil-gcloud/src/test/resources/random.json diff --git a/.travis.yml b/.travis.yml index 0ec14f396..5e74ac3fe 100644 --- a/.travis.yml +++ b/.travis.yml @@ -17,10 +17,9 @@ before_install: # Decrypt the credentials file and copy it over to the destination. - openssl aes-256-cbc -K $encrypted_ebb86cbccb5d_key -iv $encrypted_ebb86cbccb5d_iv -in credentials.tar.enc -out credentials.tar -d - tar xvf credentials.tar - - mkdir ./testutil-gcloud/src/test/resources - - cp ./spine-dev.json ./testutil-gcloud/src/test/resources/spine-dev.json - mkdir ./datastore/src/test/resources - cp ./spine-dev.json ./datastore/src/test/resources/spine-dev.json + - cp ./spine-dev.json ./testutil-gcloud/src/test/resources/spine-dev.json # Install the complete gcloud SDK to access the Datastore emulator. - ./scripts/install-gcloud.sh # Add the newly installed gcloud SDK to PATH overriding the default Travis version. diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index 154c3a0cf..26714220f 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -128,7 +128,7 @@ public static Datastore remote(Resource serviceAccount) { return datastore; } catch (IOException e) { throw newIllegalStateException( - e, "Cannot find the credentials file `%s`.", serviceAccount); + e, "Problems parsing the credentials file `%s`.", serviceAccount); } } diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java index 0d1840bb5..80d80bec4 100644 --- a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java @@ -32,6 +32,7 @@ import static com.google.common.truth.Truth.assertThat; import static io.spine.testing.server.storage.datastore.TestDatastores.DEFAULT_EMULATOR_PORT; import static java.lang.String.format; +import static org.junit.jupiter.api.Assertions.assertThrows; @DisplayName("`TestDatastores` utility should") class TestDatastoresTest extends UtilityClassTest { @@ -117,4 +118,11 @@ void byResource() { .isEqualTo(PROJECT_ID); } } + + @Test + @DisplayName("throw an `ISE` when can't properly parse account credentials from resource") + void throwOnInvalidResource() { + Resource resource = Resource.file("random.json"); + assertThrows(IllegalStateException.class, () -> TestDatastores.remote(resource)); + } } diff --git a/testutil-gcloud/src/test/resources/random.json b/testutil-gcloud/src/test/resources/random.json new file mode 100644 index 000000000..afe65fa61 --- /dev/null +++ b/testutil-gcloud/src/test/resources/random.json @@ -0,0 +1,3 @@ +{ + "random": "json" +} From 6716d9fe811a20a155a741dc82fb767ed65e582e Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Wed, 2 Oct 2019 12:53:29 +0300 Subject: [PATCH 28/30] Move the doc about the default project ID to `local(...)` methods --- .../storage/datastore/TestDatastores.java | 20 +++++++++++++------ 1 file changed, 14 insertions(+), 6 deletions(-) diff --git a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java index 26714220f..8b6d8e340 100644 --- a/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java +++ b/testutil-gcloud/src/main/java/io/spine/testing/server/storage/datastore/TestDatastores.java @@ -56,12 +56,6 @@ public final class TestDatastores implements Logging { /** * The default project ID to use when running on a local Datastore emulator. - * - *

For most tests, it's okay to use this ID even if some other project ID was passed to the - * emulator via the {@code --project} switch. - * - *

If, for some reason, you need to specify a custom project ID, please use - * {@link #local(ProjectId, int)}. */ private static final ProjectId DEFAULT_LOCAL_PROJECT_ID = ProjectId.of("test-project"); @@ -72,6 +66,13 @@ private TestDatastores() { /** * Creates a {@link Datastore} connected to the local Datastore emulator at * {@link #DEFAULT_EMULATOR_PORT}. + * + *

The {@linkplain #DEFAULT_LOCAL_PROJECT_ID default project ID} will be used. For most + * tests, it's okay to use this ID even if some other project ID was passed to the emulator via + * the {@code --project} switch. + * + *

If, for some reason, you need to specify a custom project ID, please use + * {@link #local(ProjectId, int)}. */ public static Datastore local() { return local(DEFAULT_EMULATOR_PORT); @@ -79,6 +80,13 @@ public static Datastore local() { /** * Creates a {@link Datastore} connected to the local Datastore emulator at the specified port. + * + *

The {@linkplain #DEFAULT_LOCAL_PROJECT_ID default project ID} will be used. For most + * tests, it's okay to use this ID even if some other project ID was passed to the emulator via + * the {@code --project} switch. + * + *

If, for some reason, you need to specify a custom project ID, please use + * {@link #local(ProjectId, int)}. */ public static Datastore local(int port) { return local(DEFAULT_LOCAL_PROJECT_ID, port); From 6f828b64e1e3431974cafa9aec035b52aaab53a5 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Wed, 2 Oct 2019 16:16:01 +0300 Subject: [PATCH 29/30] Fix `assertThat...` formatting --- .../datastore/SpyStorageFactoryTest.java | 3 +-- .../TestDatastoreStorageFactoryTest.java | 9 +++------ .../datastore/TestDatastoreWrapperTest.java | 12 ++++-------- .../storage/datastore/TestDatastoresTest.java | 18 ++++++------------ 4 files changed, 14 insertions(+), 28 deletions(-) diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/SpyStorageFactoryTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/SpyStorageFactoryTest.java index 75e7d1bc8..0ee50f387 100644 --- a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/SpyStorageFactoryTest.java +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/SpyStorageFactoryTest.java @@ -48,8 +48,7 @@ void injectDatastoreWrapper() { SpyStorageFactory factory = new SpyStorageFactory(); Datastore datastoreFromFactory = factory.datastore(); - assertThat(datastoreFromFactory) - .isSameInstanceAs(datastore); + assertThat(datastoreFromFactory).isSameInstanceAs(datastore); } @Test diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactoryTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactoryTest.java index bdb79090f..73d27ccea 100644 --- a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactoryTest.java +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreStorageFactoryTest.java @@ -46,8 +46,7 @@ void passNullToleranceCheck() { void wrapDatastore() { TestDatastoreStorageFactory factory = TestDatastoreStorageFactory.local(); DatastoreWrapper wrapper = factory.createDatastoreWrapper(false); - assertThat(wrapper) - .isInstanceOf(TestDatastoreWrapper.class); + assertThat(wrapper).isInstanceOf(TestDatastoreWrapper.class); } @Test @@ -64,15 +63,13 @@ void clearDatastore() { // Make sure the entity is read from the Datastore by key. Entity entityReadBeforeClear = wrapper.read(key); - assertThat(entityReadBeforeClear) - .isNotNull(); + assertThat(entityReadBeforeClear).isNotNull(); // Clear the Datastore. factory.clear(); // Make sure entity is no longer present. Entity entityReadAfterClear = wrapper.read(key); - assertThat(entityReadAfterClear) - .isNull(); + assertThat(entityReadAfterClear).isNull(); } } diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapperTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapperTest.java index c79b9424a..eb83baba5 100644 --- a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapperTest.java +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoreWrapperTest.java @@ -49,8 +49,7 @@ void waitForConsistency() { Entity entity = withKeyCreatedBy(wrapper); wrapper.createOrUpdate(entity); - assertThat(wrapper.waitedForConsistency()) - .isTrue(); + assertThat(wrapper.waitedForConsistency()).isTrue(); } @Test @@ -60,8 +59,7 @@ void notWaitForConsistency() { Entity entity = withKeyCreatedBy(wrapper); wrapper.createOrUpdate(entity); - assertThat(wrapper.waitedForConsistency()) - .isFalse(); + assertThat(wrapper.waitedForConsistency()).isFalse(); } @Test @@ -77,15 +75,13 @@ void dropAllTables() { // Make sure the entity is read from the Datastore by key. Entity entityReadBeforeClear = wrapper.read(key); - assertThat(entityReadBeforeClear) - .isNotNull(); + assertThat(entityReadBeforeClear).isNotNull(); // Drop all data. wrapper.dropAllTables(); // Make sure the entity is no longer present in the Datastore. Entity entityReadAfterClear = wrapper.read(key); - assertThat(entityReadAfterClear) - .isNull(); + assertThat(entityReadAfterClear).isNull(); } } diff --git a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java index 80d80bec4..3aac0f6e4 100644 --- a/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java +++ b/testutil-gcloud/src/test/java/io/spine/testing/server/storage/datastore/TestDatastoresTest.java @@ -54,8 +54,7 @@ void atDefaultAddress() { String host = datastore.getOptions() .getHost(); String expectedHost = format(ADDRESS_FORMAT, DEFAULT_EMULATOR_PORT); - assertThat(host) - .isEqualTo(expectedHost); + assertThat(host).isEqualTo(expectedHost); } @Test @@ -66,8 +65,7 @@ void atCustomPort() { String host = datastore.getOptions() .getHost(); String expectedHost = format(ADDRESS_FORMAT, port); - assertThat(host) - .isEqualTo(expectedHost); + assertThat(host).isEqualTo(expectedHost); } @Test @@ -81,12 +79,10 @@ void atCustomPortWithCustomId() { DatastoreOptions options = datastore.getOptions(); String host = options.getHost(); String expectedHost = format(ADDRESS_FORMAT, port); - assertThat(host) - .isEqualTo(expectedHost); + assertThat(host).isEqualTo(expectedHost); String actualProjectId = options.getProjectId(); - assertThat(actualProjectId) - .isEqualTo(id); + assertThat(actualProjectId).isEqualTo(id); } } @@ -103,8 +99,7 @@ void byResourceAtPath() { Datastore datastore = TestDatastores.remote(SPINE_DEV_JSON); String projectId = datastore.getOptions() .getProjectId(); - assertThat(projectId) - .isEqualTo(PROJECT_ID); + assertThat(projectId).isEqualTo(PROJECT_ID); } @Test @@ -114,8 +109,7 @@ void byResource() { Datastore datastore = TestDatastores.remote(serviceAccount); String projectId = datastore.getOptions() .getProjectId(); - assertThat(projectId) - .isEqualTo(PROJECT_ID); + assertThat(projectId).isEqualTo(PROJECT_ID); } } From b5ec10a8f3ca2b52bbb5ee3b59225dedf3661150 Mon Sep 17 00:00:00 2001 From: dmitrykuzmin Date: Wed, 2 Oct 2019 16:33:42 +0300 Subject: [PATCH 30/30] Remove redundant Travis config --- .travis.yml | 3 --- license-report.md | 6 +++--- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/.travis.yml b/.travis.yml index 5e74ac3fe..1925b5f2c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -17,9 +17,6 @@ before_install: # Decrypt the credentials file and copy it over to the destination. - openssl aes-256-cbc -K $encrypted_ebb86cbccb5d_key -iv $encrypted_ebb86cbccb5d_iv -in credentials.tar.enc -out credentials.tar -d - tar xvf credentials.tar - - mkdir ./datastore/src/test/resources - - cp ./spine-dev.json ./datastore/src/test/resources/spine-dev.json - - cp ./spine-dev.json ./testutil-gcloud/src/test/resources/spine-dev.json # Install the complete gcloud SDK to access the Datastore emulator. - ./scripts/install-gcloud.sh # Add the newly installed gcloud SDK to PATH overriding the default Travis version. diff --git a/license-report.md b/license-report.md index 35c64b527..5e7fcc1e3 100644 --- a/license-report.md +++ b/license-report.md @@ -734,7 +734,7 @@ The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 21:07:36 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Wed Oct 02 16:28:12 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -1474,7 +1474,7 @@ This report was generated on **Tue Oct 01 21:07:36 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 21:07:49 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Wed Oct 02 16:28:25 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). @@ -2234,4 +2234,4 @@ This report was generated on **Tue Oct 01 21:07:49 EEST 2019** using [Gradle-Lic The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Tue Oct 01 21:08:02 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file +This report was generated on **Wed Oct 02 16:28:37 EEST 2019** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file