diff --git a/plugin/trino-delta-lake/src/test/java/io/trino/plugin/deltalake/TestDeltaLakePlugin.java b/plugin/trino-delta-lake/src/test/java/io/trino/plugin/deltalake/TestDeltaLakePlugin.java index 9b85235740fa..abcfefd6ce9b 100644 --- a/plugin/trino-delta-lake/src/test/java/io/trino/plugin/deltalake/TestDeltaLakePlugin.java +++ b/plugin/trino-delta-lake/src/test/java/io/trino/plugin/deltalake/TestDeltaLakePlugin.java @@ -33,9 +33,9 @@ public class TestDeltaLakePlugin @Test public void testCreateConnector() { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); - factory.create("test", ImmutableMap.of("hive.metastore.uri", "thrift://foo:1234"), new TestingConnectorContext()); + ConnectorFactory factory = getConnectorFactory(); + factory.create("test", ImmutableMap.of("hive.metastore.uri", "thrift://foo:1234"), new TestingConnectorContext()) + .shutdown(); } @Test @@ -43,20 +43,33 @@ public void testCreateTestingConnector() { Plugin plugin = new TestingDeltaLakePlugin(); ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); - factory.create("test", ImmutableMap.of("hive.metastore.uri", "thrift://foo:1234"), new TestingConnectorContext()); + factory.create("test", ImmutableMap.of("hive.metastore.uri", "thrift://foo:1234"), new TestingConnectorContext()) + .shutdown(); + } + + @Test + public void testTestingFileMetastore() + { + ConnectorFactory factory = getConnectorFactory(); + factory.create( + "test", + ImmutableMap.of( + "hive.metastore", "file", + "hive.metastore.catalog.dir", "/tmp"), + new TestingConnectorContext()) + .shutdown(); } @Test public void testThriftMetastore() { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); + ConnectorFactory factory = getConnectorFactory(); factory.create( - "test", - ImmutableMap.of( - "hive.metastore", "thrift", - "hive.metastore.uri", "thrift://foo:1234"), - new TestingConnectorContext()) + "test", + ImmutableMap.of( + "hive.metastore", "thrift", + "hive.metastore.uri", "thrift://foo:1234"), + new TestingConnectorContext()) .shutdown(); assertThatThrownBy(() -> factory.create( @@ -74,14 +87,14 @@ public void testThriftMetastore() @Test public void testGlueMetastore() { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); + ConnectorFactory factory = getConnectorFactory(); factory.create( - "test", - ImmutableMap.of( - "hive.metastore", "glue", - "hive.metastore.glue.region", "us-east-2"), - new TestingConnectorContext()); + "test", + ImmutableMap.of( + "hive.metastore", "glue", + "hive.metastore.glue.region", "us-east-2"), + new TestingConnectorContext()) + .shutdown(); assertThatThrownBy(() -> factory.create( "test", @@ -100,9 +113,7 @@ public void testGlueMetastore() @Test public void testAlluxioMetastore() { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); - + ConnectorFactory factory = getConnectorFactory(); assertThatThrownBy(() -> factory.create( "test", ImmutableMap.of("hive.metastore", "alluxio"), @@ -121,31 +132,31 @@ public void testAlluxioMetastore() @Test public void testNoCaching() { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); + ConnectorFactory factory = getConnectorFactory(); factory.create("test", - ImmutableMap.of( - "hive.metastore.uri", "thrift://foo:1234", - "delta.metadata.cache-ttl", "0s"), - new TestingConnectorContext()); + ImmutableMap.of( + "hive.metastore.uri", "thrift://foo:1234", + "delta.metadata.cache-ttl", "0s"), + new TestingConnectorContext()) + .shutdown(); } @Test public void testNoActiveDataFilesCaching() { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); + ConnectorFactory factory = getConnectorFactory(); factory.create("test", - ImmutableMap.of( - "hive.metastore.uri", "thrift://foo:1234", - "delta.metadata.live-files.cache-ttl", "0s"), - new TestingConnectorContext()); + ImmutableMap.of( + "hive.metastore.uri", "thrift://foo:1234", + "delta.metadata.live-files.cache-ttl", "0s"), + new TestingConnectorContext()) + .shutdown(); } @Test public void testHiveConfigIsNotBound() { - ConnectorFactory factory = getOnlyElement(new DeltaLakePlugin().getConnectorFactories()); + ConnectorFactory factory = getConnectorFactory(); assertThatThrownBy(() -> factory.create("test", ImmutableMap.of( "hive.metastore.uri", "thrift://foo:1234", @@ -158,9 +169,7 @@ public void testHiveConfigIsNotBound() @Test public void testReadOnlyAllAccessControl() { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); - + ConnectorFactory factory = getConnectorFactory(); factory.create( "test", ImmutableMap.builder() @@ -174,9 +183,7 @@ public void testReadOnlyAllAccessControl() @Test public void testSystemAccessControl() { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); - + ConnectorFactory factory = getConnectorFactory(); Connector connector = factory.create( "test", ImmutableMap.builder() @@ -192,8 +199,7 @@ public void testSystemAccessControl() public void testFileBasedAccessControl() throws Exception { - Plugin plugin = new DeltaLakePlugin(); - ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); + ConnectorFactory factory = getConnectorFactory(); File tempFile = File.createTempFile("test-delta-lake-plugin-access-control", ".json"); tempFile.deleteOnExit(); Files.writeString(tempFile.toPath(), "{}"); @@ -208,4 +214,9 @@ public void testFileBasedAccessControl() new TestingConnectorContext()) .shutdown(); } + + private static ConnectorFactory getConnectorFactory() + { + return getOnlyElement(new DeltaLakePlugin().getConnectorFactories()); + } } diff --git a/plugin/trino-hive-hadoop2/src/test/java/io/trino/plugin/hive/TestHivePlugin.java b/plugin/trino-hive-hadoop2/src/test/java/io/trino/plugin/hive/TestHivePlugin.java index 682afab7fe82..3717dbfdfa21 100644 --- a/plugin/trino-hive-hadoop2/src/test/java/io/trino/plugin/hive/TestHivePlugin.java +++ b/plugin/trino-hive-hadoop2/src/test/java/io/trino/plugin/hive/TestHivePlugin.java @@ -78,6 +78,19 @@ public void testCreateConnector() factory.create("test", ImmutableMap.of("hive.metastore.uri", "thrift://foo:1234"), new TestingConnectorContext()).shutdown(); } + @Test + public void testTestingFileMetastore() + { + ConnectorFactory factory = getHiveConnectorFactory(); + factory.create( + "test", + ImmutableMap.of( + "hive.metastore", "file", + "hive.metastore.catalog.dir", "/tmp"), + new TestingConnectorContext()) + .shutdown(); + } + @Test public void testThriftMetastore() { diff --git a/plugin/trino-hudi/src/main/java/io/trino/plugin/hudi/InternalHudiConnectorFactory.java b/plugin/trino-hudi/src/main/java/io/trino/plugin/hudi/InternalHudiConnectorFactory.java index 304e4b54b2c3..fc20cc4f2919 100644 --- a/plugin/trino-hudi/src/main/java/io/trino/plugin/hudi/InternalHudiConnectorFactory.java +++ b/plugin/trino-hudi/src/main/java/io/trino/plugin/hudi/InternalHudiConnectorFactory.java @@ -30,6 +30,7 @@ import io.trino.plugin.base.classloader.ClassLoaderSafeNodePartitioningProvider; import io.trino.plugin.base.jmx.MBeanServerModule; import io.trino.plugin.base.session.SessionPropertiesProvider; +import io.trino.plugin.hive.NodeVersion; import io.trino.plugin.hive.azure.HiveAzureModule; import io.trino.plugin.hive.gcs.HiveGcsModule; import io.trino.plugin.hive.metastore.HiveMetastore; @@ -49,7 +50,7 @@ import java.util.Optional; import java.util.Set; -public class InternalHudiConnectorFactory +public final class InternalHudiConnectorFactory { private InternalHudiConnectorFactory() {} @@ -75,6 +76,7 @@ public static Connector createConnector( new HdfsFileSystemModule(), new MBeanServerModule(), binder -> { + binder.bind(NodeVersion.class).toInstance(new NodeVersion(context.getNodeManager().getCurrentNode().getVersion())); binder.bind(NodeManager.class).toInstance(context.getNodeManager()); binder.bind(TypeManager.class).toInstance(context.getTypeManager()); binder.bind(CatalogName.class).toInstance(new CatalogName(catalogName)); diff --git a/plugin/trino-hudi/src/test/java/io/trino/plugin/hudi/TestHudiPlugin.java b/plugin/trino-hudi/src/test/java/io/trino/plugin/hudi/TestHudiPlugin.java new file mode 100644 index 000000000000..c0d42e119967 --- /dev/null +++ b/plugin/trino-hudi/src/test/java/io/trino/plugin/hudi/TestHudiPlugin.java @@ -0,0 +1,133 @@ +/* + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package io.trino.plugin.hudi; + +import com.google.common.collect.ImmutableMap; +import io.airlift.bootstrap.ApplicationConfigurationException; +import io.trino.plugin.hive.HiveConfig; +import io.trino.spi.Plugin; +import io.trino.spi.connector.ConnectorFactory; +import io.trino.testing.TestingConnectorContext; +import org.testng.annotations.Test; + +import java.util.Map; +import java.util.Optional; + +import static com.google.common.collect.Iterables.getOnlyElement; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +public class TestHudiPlugin +{ + @Test + public void testCreateConnector() + { + ConnectorFactory factory = getConnectorFactory(); + factory.create("test", Map.of("hive.metastore.uri", "thrift://foo:1234"), new TestingConnectorContext()) + .shutdown(); + } + + @Test + public void testCreateTestingConnector() + { + Plugin plugin = new TestingHudiPlugin(Optional.empty()); + ConnectorFactory factory = getOnlyElement(plugin.getConnectorFactories()); + factory.create("test", Map.of("hive.metastore.uri", "thrift://foo:1234"), new TestingConnectorContext()) + .shutdown(); + } + + @Test + public void testTestingFileMetastore() + { + ConnectorFactory factory = getConnectorFactory(); + factory.create( + "test", + ImmutableMap.of( + "hive.metastore", "file", + "hive.metastore.catalog.dir", "/tmp"), + new TestingConnectorContext()) + .shutdown(); + } + + @Test + public void testThriftMetastore() + { + ConnectorFactory factory = getConnectorFactory(); + factory.create( + "test", + Map.of( + "hive.metastore", "thrift", + "hive.metastore.uri", "thrift://foo:1234"), + new TestingConnectorContext()) + .shutdown(); + } + + @Test + public void testGlueMetastore() + { + ConnectorFactory factory = getConnectorFactory(); + factory.create( + "test", + Map.of( + "hive.metastore", "glue", + "hive.metastore.glue.region", "us-east-2"), + new TestingConnectorContext()) + .shutdown(); + + assertThatThrownBy(() -> factory.create( + "test", + Map.of( + "hive.metastore", "glue", + "hive.metastore.uri", "thrift://foo:1234"), + new TestingConnectorContext())) + .isInstanceOf(ApplicationConfigurationException.class) + .hasMessageContaining("Error: Configuration property 'hive.metastore.uri' was not used"); + } + + @Test + public void testAlluxioMetastore() + { + ConnectorFactory factory = getConnectorFactory(); + assertThatThrownBy(() -> factory.create( + "test", + Map.of("hive.metastore", "alluxio"), + new TestingConnectorContext())) + .hasMessageMatching("(?s)Unable to create injector, see the following errors:.*" + + "Explicit bindings are required and HiveMetastoreFactory .* is not explicitly bound.*"); + + assertThatThrownBy(() -> factory.create( + "test", + Map.of("hive.metastore", "alluxio-deprecated"), + new TestingConnectorContext())) + // TODO: this should fail cleanly. We do not plan to support Alluxio metastore with Hudi + .hasStackTraceContaining("Cannot invoke \"String.split(String, int)\" because \"addr\" is null"); + } + + @Test + public void testHiveConfigIsNotBound() + { + ConnectorFactory factory = getConnectorFactory(); + assertThatThrownBy(() -> factory.create("test", + Map.of( + "hive.metastore.uri", "thrift://foo:1234", + // Try setting any property provided by HiveConfig class + HiveConfig.CONFIGURATION_HIVE_PARTITION_PROJECTION_ENABLED, "true"), + new TestingConnectorContext())) + .hasMessageContaining("Error: Configuration property 'hive.partition-projection-enabled' was not used"); + } + + private static ConnectorFactory getConnectorFactory() + { + return getOnlyElement(new HudiPlugin().getConnectorFactories()); + } +} diff --git a/plugin/trino-iceberg/src/test/java/io/trino/plugin/iceberg/TestIcebergPlugin.java b/plugin/trino-iceberg/src/test/java/io/trino/plugin/iceberg/TestIcebergPlugin.java index a249f2a72770..f048fd8f787c 100644 --- a/plugin/trino-iceberg/src/test/java/io/trino/plugin/iceberg/TestIcebergPlugin.java +++ b/plugin/trino-iceberg/src/test/java/io/trino/plugin/iceberg/TestIcebergPlugin.java @@ -38,17 +38,30 @@ public void testCreateConnector() factory.create("test", Map.of("hive.metastore.uri", "thrift://foo:1234"), new TestingConnectorContext()).shutdown(); } + @Test + public void testTestingFileMetastore() + { + ConnectorFactory factory = getConnectorFactory(); + factory.create( + "test", + Map.of( + "iceberg.catalog.type", "TESTING_FILE_METASTORE", + "hive.metastore.catalog.dir", "/tmp"), + new TestingConnectorContext()) + .shutdown(); + } + @Test public void testThriftMetastore() { ConnectorFactory factory = getConnectorFactory(); factory.create( - "test", - Map.of( - "iceberg.catalog.type", "HIVE_METASTORE", - "hive.metastore.uri", "thrift://foo:1234"), - new TestingConnectorContext()) + "test", + Map.of( + "iceberg.catalog.type", "HIVE_METASTORE", + "hive.metastore.uri", "thrift://foo:1234"), + new TestingConnectorContext()) .shutdown(); // Ensure Glue configuration isn't bound when Glue not in use @@ -81,11 +94,11 @@ public void testGlueMetastore() ConnectorFactory factory = getConnectorFactory(); factory.create( - "test", - Map.of( - "iceberg.catalog.type", "glue", - "hive.metastore.glue.region", "us-east-1"), - new TestingConnectorContext()) + "test", + Map.of( + "iceberg.catalog.type", "glue", + "hive.metastore.glue.region", "us-east-1"), + new TestingConnectorContext()) .shutdown(); assertThatThrownBy(() -> factory.create( @@ -97,12 +110,12 @@ public void testGlueMetastore() .hasMessageContaining("Error: Configuration property 'hive.metastore.uri' was not used"); factory.create( - "test", - Map.of( - "iceberg.catalog.type", "glue", - "hive.metastore.glue.catalogid", "123", - "hive.metastore.glue.region", "us-east-1"), - new TestingConnectorContext()) + "test", + Map.of( + "iceberg.catalog.type", "glue", + "hive.metastore.glue.catalogid", "123", + "hive.metastore.glue.region", "us-east-1"), + new TestingConnectorContext()) .shutdown(); } @@ -113,12 +126,12 @@ public void testRecordingMetastore() // recording with thrift factory.create( - "test", - Map.of( - "iceberg.catalog.type", "HIVE_METASTORE", - "hive.metastore.uri", "thrift://foo:1234", - "hive.metastore-recording-path", "/tmp"), - new TestingConnectorContext()) + "test", + Map.of( + "iceberg.catalog.type", "HIVE_METASTORE", + "hive.metastore.uri", "thrift://foo:1234", + "hive.metastore-recording-path", "/tmp"), + new TestingConnectorContext()) .shutdown(); // recording with glue @@ -138,13 +151,13 @@ public void testAllowAllAccessControl() ConnectorFactory connectorFactory = getConnectorFactory(); connectorFactory.create( - "test", - ImmutableMap.builder() - .put("iceberg.catalog.type", "HIVE_METASTORE") - .put("hive.metastore.uri", "thrift://foo:1234") - .put("iceberg.security", "allow-all") - .buildOrThrow(), - new TestingConnectorContext()) + "test", + ImmutableMap.builder() + .put("iceberg.catalog.type", "HIVE_METASTORE") + .put("hive.metastore.uri", "thrift://foo:1234") + .put("iceberg.security", "allow-all") + .buildOrThrow(), + new TestingConnectorContext()) .shutdown(); } @@ -154,13 +167,13 @@ public void testReadOnlyAllAccessControl() ConnectorFactory connectorFactory = getConnectorFactory(); connectorFactory.create( - "test", - ImmutableMap.builder() - .put("iceberg.catalog.type", "HIVE_METASTORE") - .put("hive.metastore.uri", "thrift://foo:1234") - .put("iceberg.security", "read-only") - .buildOrThrow(), - new TestingConnectorContext()) + "test", + ImmutableMap.builder() + .put("iceberg.catalog.type", "HIVE_METASTORE") + .put("hive.metastore.uri", "thrift://foo:1234") + .put("iceberg.security", "read-only") + .buildOrThrow(), + new TestingConnectorContext()) .shutdown(); } @@ -191,14 +204,14 @@ public void testFileBasedAccessControl() Files.writeString(tempFile.toPath(), "{}"); connectorFactory.create( - "test", - ImmutableMap.builder() - .put("iceberg.catalog.type", "HIVE_METASTORE") - .put("hive.metastore.uri", "thrift://foo:1234") - .put("iceberg.security", "file") - .put("security.config-file", tempFile.getAbsolutePath()) - .buildOrThrow(), - new TestingConnectorContext()) + "test", + ImmutableMap.builder() + .put("iceberg.catalog.type", "HIVE_METASTORE") + .put("hive.metastore.uri", "thrift://foo:1234") + .put("iceberg.security", "file") + .put("security.config-file", tempFile.getAbsolutePath()) + .buildOrThrow(), + new TestingConnectorContext()) .shutdown(); } @@ -208,12 +221,12 @@ public void testIcebergPluginFailsWhenIncorrectPropertyProvided() ConnectorFactory factory = getConnectorFactory(); assertThatThrownBy(() -> factory.create( - "test", - Map.of( - "iceberg.catalog.type", "HIVE_METASTORE", - HIVE_VIEWS_ENABLED, "true", - "hive.metastore.uri", "thrift://foo:1234"), - new TestingConnectorContext()) + "test", + Map.of( + "iceberg.catalog.type", "HIVE_METASTORE", + HIVE_VIEWS_ENABLED, "true", + "hive.metastore.uri", "thrift://foo:1234"), + new TestingConnectorContext()) .shutdown()) .isInstanceOf(ApplicationConfigurationException.class) .hasMessageContaining("Configuration property 'hive.hive-views.enabled' was not used");