如何使用内存中的derby数据库进行hive(scala)测试

zqdjd7g9  于 2021-06-26  发布在  Hive
关注(0)|答案(1)|浏览(641)

我正在使用SparkHive2.3.0和Scala2.11,并建立一个单元测试框架。星火Hive TestHiveContext 以及 TestHiveSparkSession 它可以方便地从单元测试中调用配置单元,而无需运行hadoop、spark或集群,这对于自动化测试非常有用。
hive需要一个数据库作为它的元存储,当以这种方式运行时,它使用derby作为配置了的嵌入式数据库 javax.jdo.option.ConnectionURL 默认情况下 jdbc:derby:;databaseName=<file-path>;create=true . 这个 <file-path> 是本地文件系统中的一个位置,是运行derby的一个选项。
另一个选择是在内存中运行derby,这通常与将此url更改为 jdbc:derby:memory:databaseName;create=true . 但是,这在配置单元中是不可能的,因为配置是在内部 HiveUtils 类,无法重写。我曾尝试在我的spark会话生成器中更改它,但后来我的更改被 HiveUtils 当我创建我的 TestHiveContext .
在我的例子中,内存数据库更可取,因为我们的开发人员在windows上运行(绝对不是我/我们的选择),而且在创建这些文件时,常常会出现权限或文件名中的无效字符等问题(因为hadoop从未真正打算在windows上运行),这些文件经常被留下,因为它们不能被清理(由于这些问题)。我们希望测试是完全独立的,这样就可以在没有副作用的情况下运行和完成,这样就可以在多个环境中运行(developer、ci、jenkins、aws等)。
有趣的是,我在 TestHive.scala :

{ // set the metastore temporary configuration
  val metastoreTempConf = HiveUtils.newTemporaryConfiguration(useInMemoryDerby = false) ++ Map(

因此,有一个用于使用内存中数据库的标志,但这是不可配置的,并且没有设置为的代码路径 true .
有没有什么方法来配置或编写它以便 TestHive 的德比能在记忆中吗?正在尝试设置 javax.jdo.option.ConnectionURL 不管是hive-site.xml还是hdfs-site.xml都不起作用,我认为这是因为 TestHive , TestHiveContext 以及 TestHiveSparkSession 初始化时,它们有自己的代码路径与非测试路径分开。它们提供的功能对测试框架非常有用,但显然没有提供覆盖此值和其他一些设置的方法。
到目前为止,我能看到的最好的选择是重写或编写我自己的 TestHiveContext 类,它从该类中借用了一系列功能并重写了我需要的部分,但对于我认为可以通过简单的配置更改来完成的任务来说,这是一个相对较大的任务。

kkbh8khc

kkbh8khc1#

我终于想出了如何做到这一点,并想分享答案,以防其他人试图做同样的事情。
我的测试班使用 SharedSparkContext 特质,它提供了 SparkContext 通过var引用 sc .
在sparkcontext初始化之后(我使用 beforeAll 钩子可用于 scalatest 测试框架),我创建了一个 TestHiveContext 这样地:

hc = new TestHiveContext(sc, false)

紧接着,我可以设置 javax.jdo.option.ConnectionURL 大概还有其他一些hadoop和hive配置,比如:

sc.hadoopConfiguration.set("javax.jdo.option.ConnectionURL", 
                           "jdbc:derby:memory:db;create=true")

此配置参数由配置单元使用,但显然必须添加到hadoop配置中,hadoop配置用于构建配置单元测试上下文。
诀窍是计时,这必须在hadoop和hive自己初始化之后完成(使用配置文件等等),scalatest框架也被初始化,最后在testhive框架初始化之后,但是在运行任何测试之前。在其他初始化之前尝试设置此参数意味着在测试运行之前将覆盖您的设置。

相关问题