alter table abc add columns (stats1 map<string,string>, stats2 map<string,string>)
上記のクエリでテーブルを変更しました。しかし、データをチェックしているうちに、両方の余分な列が NULL になりました。私はデータを取得していません。
alter table abc add columns (stats1 map<string,string>, stats2 map<string,string>)
上記のクエリでテーブルを変更しました。しかし、データをチェックしているうちに、両方の余分な列が NULL になりました。私はデータを取得していません。
パーティション テーブルに列を追加するには、パーティションを再作成する必要があります。表が外部で、データファイルにすでに新しい列が含まれているとします。次の手順を実行します。 1. 表の変更 列の追加... 2. パーティションを再作成します。パーティションごとに、ドロップしてから作成します。新しく作成されたパーティション スキーマは、テーブル スキーマを継承します。
または、テーブルを削除してからテーブルを作成し、すべてのパーティションを作成するか、単にMSCK REPAIR TABLE abc
コマンドを実行してそれらを復元することができます。Amazon Elastic MapReduce (EMR) のバージョンの Hive で同等のコマンドは次のとおりALTER TABLE table_name RECOVER PARTITIONS
です。こちらのマニュアルを参照してください: RECOVER PARTITIONS
また、Hive 1.1.0 以降では、CASCADE
のオプションを使用できますALTER TABLE ADD|REPLACE COLUMNS
。こちらのマニュアルを参照してください: ADD COLUMN
これらの提案は、外部テーブルで機能します。
このソリューションは、データがパーティション分割されていて、最新のパーティションの場所がわかっている場合にのみ機能します。この場合、コストのかかる操作であるパーティションの回復または修復を行う代わりに、次のようなことができます。
参照用にスカラ コードを投稿する:
def updateMetastoreColumns(spark: SparkSession, partitionedTablePath: String, toUpdateTableName: String): Unit = {
//fetch all column names along with their corresponding datatypes from latest partition
val partitionedTable = spark.read.orc(partitionedTablePath)
val partitionedTableColumns = partitionedTable.columns zip partitionedTable.schema.map(_.dataType.catalogString)
//fetch all column names along with their corresponding datatypes from currentTable
val toUpdateTable = spark.read.table(toUpdateTableName)
val toUpdateTableColumns = toUpdateTable.columns zip toUpdateTable.schema.map(_.dataType.catalogString)
//check if new columns are present in newer partition
val diffColumns = partitionedTableColumns.diff(toUpdateTableColumns)
//update the metastore with new column info
diffColumns.foreach {column: (String, String) => {
spark.sql(s"ALTER TABLE ${toUpdateTableName} ADD COLUMNS (${column._1} ${column._2})")
}}
}
これにより、新しいパーティションに追加された最新の列を動的に見つけて、その場でメタストアに更新することができます。