SQLException上的sqlContext HiveDriver错误:不支持方法
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了SQLException上的sqlContext HiveDriver错误:不支持方法相关的知识,希望对你有一定的参考价值。
我一直在尝试使用sqlContext.read.format("jdbc").options(driver="org.apache.hive.jdbc.HiveDriver")
将Hive表放入Spark而没有任何成功。我做过研究并阅读如下:
How to connect to remote hive server from spark
Spark 1.5.1 not working with hive jdbc 1.2.0
http://belablotski.blogspot.in/2016/01/access-hive-tables-from-spark-using.html
我使用了最新的Hortonworks Sandbox 2.6并向社区询问了同样的问题:
通过pyspark
,我想做的事情非常简单:
df = sqlContext.read.format("jdbc").options(driver="org.apache.hive.jdbc.HiveDriver", url="jdbc:hive2://localhost:10016/default", dbtable="sample_07",user="maria_dev", password="maria_dev").load()
这给了我这个错误:
17/12/30 19:55:14 INFO HiveConnection: Will try to open client transport with JDBC Uri: jdbc:hive2://localhost:10016/default
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/hdp/current/spark-client/python/pyspark/sql/readwriter.py", line 139, in load
return self._df(self._jreader.load())
File "/usr/hdp/current/spark-client/python/lib/py4j-0.9-src.zip/py4j/java_gateway.py", line 813, in __call__
File "/usr/hdp/current/spark-client/python/pyspark/sql/utils.py", line 45, in deco
return f(*a, **kw)
File "/usr/hdp/current/spark-client/python/lib/py4j-0.9-src.zip/py4j/protocol.py", line 308, in get_return_value
py4j.protocol.Py4JJavaError: An error occurred while calling o119.load.
: java.sql.SQLException: Method not supported
at org.apache.hive.jdbc.HiveResultSetMetaData.isSigned(HiveResultSetMetaData.java:143)
at org.apache.spark.sql.execution.datasources.jdbc.JDBCRDD$.resolveTable(JDBCRDD.scala:136)
at org.apache.spark.sql.execution.datasources.jdbc.JDBCRelation.<init>(JDBCRelation.scala:91)
at org.apache.spark.sql.execution.datasources.jdbc.DefaultSource.createRelation(DefaultSource.scala:57)
at org.apache.spark.sql.execution.datasources.ResolvedDataSource$.apply(ResolvedDataSource.scala:158)
at org.apache.spark.sql.DataFrameReader.load(DataFrameReader.scala:119)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at py4j.reflection.MethodInvoker.invoke(MethodInvoker.java:231)
at py4j.reflection.ReflectionEngine.invoke(ReflectionEngine.java:381)
at py4j.Gateway.invoke(Gateway.java:259)
at py4j.commands.AbstractCommand.invokeMethod(AbstractCommand.java:133)
at py4j.commands.CallCommand.execute(CallCommand.java:79)
at py4j.GatewayConnection.run(GatewayConnection.java:209)
at java.lang.Thread.run(Thread.java:748)
使用直线,它工作正常
beeline> !connect jdbc:hive2://localhost:10016/default maria_dev maria_dev
Connecting to jdbc:hive2://localhost:10016/default
Connected to: Spark SQL (version 2.1.1.2.6.1.0-129)
Driver: Hive JDBC (version 1.2.1000.2.6.1.0-129)
Transaction isolation: TRANSACTION_REPEATABLE_READ
0: jdbc:hive2://localhost:10016/default> select * from sample_07 limit 2;
+----------+-------------------------+------------+---------+--+
| code | description | total_emp | salary |
+----------+-------------------------+------------+---------+--+
| 00-0000 | All Occupations | 134354250 | 40690 |
| 11-0000 | Management occupations | 6003930 | 96150 |
+----------+-------------------------+------------+---------+--+
我也可以这样做:
spark = SparkSession.Builder().appName("testapp").enableHiveSupport().getOrCreate()
spark.sql("select * from default.sample_07").collect()
但是这会直接读入Hive元数据。我想将JDBC用于Spark Thrift Server以实现细粒度的安全性。
我可以像这样做PostgreSQL:
sqlContext.read.format("jdbc").options(driver="org.postgresql.Driver")
我也可以使用Scala java.sql.{DriverManager, Connection, Statement, ResultSet}
创建JDBC Connection作为客户端来获取Spark。但这基本上将所有数据放入内存,然后手动重新创建Dataframe。
所以问题是:有没有办法用Hive表数据创建Spark数据帧而不将数据加载到像Scala这样的JDBC客户端中,而不是像上面的例子那样使用SparkSession.Builder()
?我的用例是我需要处理细粒度的安全性。
我不确定我是否正确理解你的问题,但是根据我的理解,你需要在数据框中获得一个hive表,因为你不需要有JDBC连接,在你的示例链接中它们是尝试连接到不同的数据库(RDBMS),而不是Hive。
请参阅下面的方法,使用hive上下文,您可以将表格放入数据框中。
import org.apache.spark.SparkConf
import org.apache.spark.SparkContext
import org.apache.spark.sql.{DataFrame, SQLContext}
def main(args: Array[String]): Unit = {
val sparkConf = new SparkConf().setAppName("APPName")
val sc = new SparkContext(sparkConf)
val hiveContext = new org.apache.spark.sql.hive.HiveContext(sc)
val sqlContext = new SQLContext(sc)
val hive_df = hiveContext.sql("select * from schema.table").first()
//other way
// val hive_df= hiveContext.table ("SchemaName.TableName")
//Below will print the first line
df.first()
//count on dataframe
df.count()
}
如果你真的想使用JDBC连接,我有以下用于Oracle数据库的例子,这可能对你有所帮助。
val oracle_data = sqlContext.load("jdbc", Map("url" -> "jdbc:oracle:thin:username/password//hostname:2134/databaseName", "dbtable" -> "Your query tmp", "driver" -> "oracle.jdbc.driver.OracleDriver"));
其实我调查了这个。 Hortonworks和cloudera正在停止通过Thrift服务器从Spark连接到hive的支持。
所以你正在做一些不可能的事情。
链接说节俭是禁用的,但它是专门从火花蜂巢。我可以从除了hive之外的spark连接到所有类型的数据库。
因此,您必须处理不同类型的授权。
由于火花对象直接连接到蜂巢,他们正在移除节俭支撑。
从您之前的问题,它能够读取数据,但读取错误的数据。 Spark 2.2 Thrift server error on dataframe NumberFormatException when query Hive table
码
>>> df = sqlContext.read.format("jdbc").options(driver="org.apache.hive.jdbc.HiveDriver", url="jdbc:hive2://localhost:10016/default", dbtable="test4",user="hive", password="hive").option("fetchsize", "10").load()
>>> df.select("*").show()
+---+----+
| id|desc|
+---+----+
| id|desc|
| id|desc|
+---+----+
这里的问题在于蜂巢
默认方言中引用标识符的默认方式是使用双引号。像SELECT“dw_date”FROM table ...这样的SQL查询将由Hive解析以选择字符串文字,而不是名为“dw_date”的列。通过用反引号替换引号,问题似乎已得到解决。但是,在我的测试中,来自Hive的列名称都以表名为table.dw_date为前缀。但是你不能像table.dw_date
一样直接包裹它。或者,我们需要单独包装每个部分
码
private case object HiveDialect extends JdbcDialect {
override def canHandle(url : String): Boolean = url.startsWith("jdbc:hive2")
override def quoteIdentifier(colName: String): String = {
colName.split(‘.’).map(part => s”`$part`”).mkString(“.”)
}
}
请按照下面的帖子来实施解决方案。
https://medium.com/@viirya/custom-jdbc-dialect-for-hive-5dbb694cc2bd
以上是关于SQLException上的sqlContext HiveDriver错误:不支持方法的主要内容,如果未能解决你的问题,请参考以下文章
conn.rollback() 上的错误未处理 SQLException...如何正确使用 commit()?
SqlException (0x80131904):在 Azure 上托管的 .NET 6 WebAPI 上的用户“dbuser”登录失败
Solr上的数据导入失败,带有SQLException:单行子查询返回多行
ManyToMany 属性的 SELECT 上的 JPQL Hibernate SQLException
原因:java.sql.SQLException:无法删除表“投票”上的外键约束“FK336ctjyksuuwnpmffcogcdyet”引用的表“链接”