我有一个像下面这样的hive表
create external table transaction(
id int,
name varchar(60))
month string
)
PARTITIONED BY (
year string,
transaction_type_code varchar(20)
)
STORED AS PARQUET
LOCATION 'hdfs://xyz';
我正在创建一个外部表,其中有一个分区列dt
,如下所示
create external table transaction_copy(
id int,
name varchar(60))
month string
)
PARTITIONED BY (
dt string,
year string,
transaction_type_code varchar(20)
)
STORED AS PARQUET
LOCATION 'hdfs://xyz';
添加如下的分区
alter table transaction_copy add if not exists partition (dt='20210811') LOCATION 'hdfs://xyz';
低于异常
ERROR: Error while compiling statement: FAILED: ValidationFailureSemanticException partition spec {dt=20210810} doesn't contain all (3) partition columns
我可以通过传递所有3个分区来添加分区。
是否可以只传递一个分区?
不可能添加分区并只指定三列中的一列,因为Hive中的分区是分层的,在hdfs中分区是分层的文件夹:
table location
----------------------
| | ...
dt1 dt2 ...
______________... __________
| | | |
year=1 year=2 year3 ....
... |
-------------------------
| |
transaction_type_code = 1 transaction_type_code = 2
hdfs://blabla-my-dwh/table_name/dt=1/year=1/transaction_type_code=1
每个分区位置路径如下所示数据文件通常位于叶子路径文件夹中,但是,您可以在hdfs中指定一些不属于这个层次结构的自定义位置,但是分区的元数据应该包含所有列,因为没有所有列,根本无法识别分区。
顺便说一句,如果dt
是一个日期,year
可以从相同的dt
派生,那么这样的分区是没有意义的,因为每个日期只包含一年。
另外,如果您正在创建具有三个分区列的外部表,请确保您已经在分层文件夹中组织了数据,除非您要手动为每个分区指定一些自定义位置。CREATE EXTERNAL TABLE不会为您重新组织数据,如果每个分区没有数据文件夹,它将无法工作。
如果您有一个已经分区的表,并且希望使用不同的分区模式重新分区,那么您需要重新加载数据:
- 创建新的分区表
set hive.exec.dynamic.partition=true;
set hive.exec.dynamic.partition.mode=nonstrict;
insert overwrite table my_new_table partition (day, month, year)
select col1, col2 ...,
day, month, year --partition columns shold be the last
from my_old_table;
- 删除旧表(删除文件夹,如果你不需要它),重命名新表