Hive sql写法问题导致结果异常合集(一)
1.扫描分区过多,元数据中拼接查询报错
现象:
任务报错,hiveserver日志或者客户端返回大量part_name= ?
原因:
分区过多,元数据sql拼接过长,每一个Part_name的打印就是一扫描了一个分区
解决方法:
整改sql,减少分区遍历量,当前发现2000分区以下可正常遍历
可通过explain authorization sql;打执行计划查看input出分区小于2000分区以下即可
2.cascade级联修改表字段
现象:
修改超时,有可能导致dbservice异常
原因:
级联修改表字段,例如如下sql
Alter table tb_1 add cloumns id string cascade;
会将表分区的字段都进行修改,会在元数据库中启动事务新增分区数*字段数条记录再删除之前的分区数*字段数条记录,在分区和字段多情况下为重量级操作
解决方法:
- 修改不加cascade,不级联修改时,如往历史分区插入数据,新增的字段由于无元数据,查询显示为null
- 重建表,历史数据重新导入新表
3.alter table drop partition 删除大量分区
现象:
删除慢,有可能导致dbservice异常
原因:
删除分区会关联删除大量元数据表,例如Partitions,partition_params,为重量级操作
解决方法:
分批删除,1000个分区以下一批
4.大分区表查询不带分区
现象:
查询慢,可能导致Hiveserver fullgc
原因:
分区多,全表扫描对元数据和hdfs都存在考验
解决方法:
查询带分区进行查询
5.sparksql嵌套过多、大量case when
现象:
编译解析sql生成代码时候,driver内存调至70GB仍出现oom
原因:
在参数spark.sql.codegen.wholeStage为true(默认true)时候,全阶段代码生成(Whole-stage Code Generation)这个是针对整个sql进行的代码生成,当sql嵌套过于复杂,逻辑过多,driver在生成代码过程的压力就会过大,发生oom
解决办法:
1.整改sql
2.开启spark.sql.codegen.wholeStage为false,开启后driver侧不生成完整的java代码,效率会慢一点
6.sparksql 没有group by 情况下使用Having
现象:
编译报错
原因:
正常情况下having使用在group by后筛选分组后的各组数据,Spark2.3未规范校验having,执行正常,spark2.4开始严格校验,导致版本间存在差异
解决办法:
- 整改sql,用where代替having规范使用
- 4设置参数spark.sql.legacy.parser.havingWithoutGroupByAsWhere为true
- 点赞
- 收藏
- 关注作者
评论(0)