Spark写入hive表时saveAsTable和insertInto的区别/Spark插入hive分区表的一些坑(原创)
saveAsTable和insertInto区别
Spark 提供了两种写入hive的模式saveAsTable, insertInto
1.saveAstable–官方文档
落地dataframe到具体表中,当mode=overwrite 则schema不需要和已经存在的表相同,说人话:使用overwrite如果表不存在则创建 ,如果存在在会按照指定位置插入原有数据
对应 mode=overwrit,这里面有个坑需要注意一下,再详细说明一下:
1)如果表不存在:自动创建
2)如果表存在:分为一下两种情况:
a.dataframe的schema与已存在的schema个数相同:不需要考虑名称是否一致,会在指定位置进行插入
(这一点区别insertInto)
b.dataframe的schema与已存在的schema个数不同:会撇弃原有的schema,按照dataframe的schema重新创建并插 入。
当schema存在时依赖以下几种存储模式:
- append :追加数据到已存在的表
- overwrite:覆盖已存在的数据
- error or errorifexsists:数据已存在则抛出异常(默认)
- ignore:数据/分区已存在忽略,不会插入数据
2.insertInto–官方文档
与saveAsTable 最大的区别就是要求表必须存在否则插入会报错,并且dateframe的schema与目标表的schema字段个数要保持一致。
插入HIVE分区表,要求重复插入同一天要覆盖当天分区,而不会覆盖整张表
**插入hive分区表坑之:saveAsTable **
report_info.write.partitionBy("time_d","time_h","time_m").saveAsTable(name="dwd.t_dwd_report_info_m",mode='overwite')
会发现整个表的分区都被覆盖,这并不是我们想要的结果。
**插入动态分区:insertInto **
#首先加入以下参数开启动态分区
sqlContext.conf.set("spark.sql.parquet.writeLegacyFormat","true")
sqlContext.conf.set("spark.sql.sources.partitionOverwriteMode","dynamic")
report_info.write.insertInto(tableName="dwd.t_dwd_report_info_m",overwrite=True)
#成功插入并覆盖当前分区,不会覆盖其他分区 在插入之前先创建分区表,或者使用saveAsTable生成表再插入。