Spark 3.3.0含特殊字符列过滤报错问题求助
解决Spark 3.3.0中JDBC读取SAP数据库后含特殊字符列的过滤报错问题
问题重现
Spark 3.2.1通过JDBC读取SAP数据库时,使用df.filter("/ABC/COLUMN = 'ID_HERE'")能正常过滤含斜杠的特殊列;升级到Spark 3.3.0后,触发ParseException,提示斜杠位置语法错误,但本地创建含特殊字符的表并过滤无此问题。
可行解决方案
方案1:使用DataFrame列引用替代SQL字符串表达式
绕开Spark SQL解析器的限制,直接通过DataFrame的列对象进行过滤,两种写法均可:
# 方式1:直接用DataFrame索引引用列 df_2 = df_1.filter(df_1["`/ABC/COLUMN`"] == 'ID_HERE') # 方式2:使用col函数(需提前导入) from pyspark.sql.functions import col df_2 = df_1.filter(col("`/ABC/COLUMN`") == 'ID_HERE')
方案2:读取后重命名特殊字符列
在读取数据后,将含特殊字符的列重命名为常规名称,后续过滤直接使用新名称:
# 读取数据后重命名特殊列 df_1 = df_1.withColumnRenamed("`/ABC/COLUMN`", "abc_column") # 使用新列名执行过滤 df_2 = df_1.filter("abc_column = 'ID_HERE'")
方案3:在JDBC读取阶段完成过滤(数据库端执行)
如果过滤逻辑允许在数据库层面执行,直接通过query参数替代dbtable,让SAP数据库提前完成过滤,避免Spark端解析特殊列:
df_2 = spark.read.format("jdbc") \ .option("url", "URL_LINK") \ .option("query", 'SELECT * FROM DATABASE."/ABC/TABLE" WHERE "/ABC/COLUMN" = \'ID_HERE\'') \ .option("user", "USER_HERE") \ .option("password", "PW_HERE") \ .option("driver", "com.sap.db.jdbc.Driver") \ .load()
问题原因
Spark 3.3.0对SQL标识符的解析规则做了严格调整,JDBC读取的SAP表元数据中,含斜杠的列名在SQL表达式解析时未被正确识别为合法标识符;而本地创建的表由Spark自身管理元数据,解析逻辑兼容特殊字符,因此无报错。
内容的提问来源于stack exchange,提问作者Thiago Vieira
相关产品推荐
相关产品推荐

