使用 Kerberos 将 RStudio(但不是 R)连接到 Hive 的问题

Issue connecting RStudio (but not R) to Hive with Kerberos

我正在尝试将 RStudio 连接到具有 Kerberos 身份验证的 Hive。如果我 运行 在从命令行调用的 R 脚本中执行以下操作,它就可以工作。

library("DBI")
library("rJava")
library("RJDBC")

cp = c("/u01/cloudera/parcels/CDH/lib/hive/lib/hive-jdbc.jar"
, "/u01/cloudera/parcels/CDH/lib/hadoop/hadoop-common.jar"
, "/u01/cloudera/parcels/CDH/lib/hive/lib/libthrift-0.9.2.jar"
, "/u01/cloudera/parcels/CDH/lib/hive/lib/hive-service.jar"
, "/u01/cloudera/parcels/CDH/lib/hive/lib/httpclient-4.2.5.jar"
, "/u01/cloudera/parcels/CDH/lib/hive/lib/httpcore-4.2.5.jar"
, "/u01/cloudera/parcels/CDH/lib/hive/lib/hive-jdbc-standalone.jar")
.jinit(classpath=cp)

drv <- JDBC("org.apache.hive.jdbc.HiveDriver" , "hive-jdbc.jar" )

conn <- dbConnect(drv , "jdbc:hive2://XXXX:10000/default;principal=hive/XXXX@XXXXX";auth-kerberos)

如果我 运行 在 RStudio 中使用完全相同的脚本,我会得到一个错误:

javax.security.sasl.SaslException: GSS initiate failed [Caused by GSSException: No valid credentials provided (Mechanism level: Failed to find any Kerberos tgt)]

如果我在 RStudio 中 运行 system('klist'),它显示我有一张有效的票。似乎 RStudio 无法识别票证,但 R 可以。有什么想法吗?

首先是一些无聊的东西,把事情放在上下文中,然后是解决方案。

  • Kerberos:它本质上很复杂(想想密码学网络,即使不考虑微软有自己的实现和扩展
  • Java 和 Kerberos:更复杂 (仅部分支持,Java 版本中的细微变化等)
  • Hadoop 和 Java 以及 Kerberos:它既复杂又丑陋 (如果你真的想失去理智,请阅读 GitBook "Hadoop and Kerberos, the Madness beyond the Gate") 而且它甚至Windows 比照更糟。缺少所需 Hadoop 的官方构建 "native libs"
  • Hive 和 JDBC 以及 Kerberos:好消息是您不需要 Hadoop "ugly" 部分 除非 您使用的是 Apache JDBC Windows 上的驱动程序(提示:抛弃它并选择 Cloudera JDBC 驱动程序!);坏消息是您可能需要原始 JAAS 配置和特定的 Java 系统属性
  • R 和 Java/JDBC:它工作得很好,除了有时你想将特定的 Java 系统属性传递给 JVM——在启动时或在 运行 时-- 但 .jinit 不支持那个 AFAIK,你必须求助于解决方法


有一个 Java 系统 属性 必须设置 Kerberos 身份验证才能在 JDBC 中工作,并且它并不总是默认设置。
但是您不能直接从 R 设置 Java 属性;你必须设置一个环境变量 (在启动R之前,或者从R代码但在.jinit之前)

选项 1: 来自 Linux shell 脚本,在启动 R 之前...

export JAVA_TOOL_OPTIONS="-Djavax.security.auth.useSubjectCredsOnly‌​=false"

选项 2: 来自您的 R 代码...

Sys.setenv(JAVA_TOOL_OPTIONS="-Djavax.security.auth.useSubjectCredsOnly‌​=false")
.jinit(...)


现在,这可能在所有情况下都不够。也许您需要使用特定的 Kerberos 配置,因为您的 Hadoop 集群使用它自己的 KDC。也许您不想使用默认的 Kerberos 票证,而是使用存储在密钥表文件中的密码作为服务帐户进行身份验证。
也许你需要一些调试信息,因为,好吧,狗屎发生了(默认情况下,安全库非常隐秘,我想这不是为了让黑客太容易做事......)

请参阅 了解有关 高级 Java 配置的更多信息 Hive/Impala JDBC 和 Kerberos

设置环境变量时要小心:模拟一个Java命令行即-Dsome.key=value -Dsome.other.key=blahblah;在 shell 脚本中,使用引号(因为分隔 space);在 R 代码中,使用单个字符串,不使用数组。