Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sql BigQuery:使用DML以原子方式替换日期分区_Sql_Google Bigquery - Fatal编程技术网

Sql BigQuery:使用DML以原子方式替换日期分区

Sql BigQuery:使用DML以原子方式替换日期分区,sql,google-bigquery,Sql,Google Bigquery,我经常想将一天的数据加载到一个日期分区的BigQuery表中,替换已经存在的任何数据。我知道如何对“旧式”数据分区表(具有\u PARTITIONTIME字段的表)执行此操作,但不知道如何对新样式的日期分区表执行此操作(这些表使用普通的日期/时间戳列来指定分区,因为它们不允许使用$装饰器) 假设我想在my_table上执行此操作。对于旧式的日期分区表,我使用使用$装饰器和WRITE\u TRUNCATEWRITE处置的加载作业来完成此操作——例如,我将目标表设置为my_table$2018100

我经常想将一天的数据加载到一个日期分区的BigQuery表中,替换已经存在的任何数据。我知道如何对“旧式”数据分区表(具有
\u PARTITIONTIME
字段的表)执行此操作,但不知道如何对新样式的日期分区表执行此操作(这些表使用普通的日期/时间戳列来指定分区,因为它们不允许使用
$
装饰器)

假设我想在
my_table
上执行此操作。对于旧式的日期分区表,我使用使用
$
装饰器和
WRITE\u TRUNCATE
WRITE处置的加载作业来完成此操作——例如,我将目标表设置为
my_table$20181005

但是,我不知道如何使用DML执行等效的操作。我发现自己在执行单独的
DELETE
INSERT
命令。这并不好,因为它增加了复杂性、查询数量,而且操作不是原子的

我想知道如何使用
MERGE
命令来实现这一点,以使所有这些都包含在一个单一的原子操作中。但是,我无法理解MERGE命令的语法,也没有找到此用例的示例。有人知道应该如何实现吗

理想的答案是一个DML语句,它从
源表
中选择所有列,并将其插入
我的表
日期分区,删除
我的表
2018-10-05
日期分区中的任何现有数据e
my_table
具有相同的架构,并且
my_table
day
列上进行分区,该列的类型为
DATE

因为他们不允许一个人使用$decorator

但它们确实如此——当您加载到基于列的分区表中时,也可以使用
表名$YYYYMMDD

$ bq query --use_legacy_sql=false "CREATE TABLE tmp_elliottb.PartitionedTable (x INT64, y NUMERIC, date DATE) PARTITION BY date"
然后我加载到一个特定的分区:

$ echo "1,3.14,2018-11-07" > row.csv
$ bq load "tmp_elliottb.PartitionedTable\$20181107" ./row.csv
$ echo "2,0.11,2018-11-07" > row.csv
$ bq load --replace "tmp_elliottb.PartitionedTable\$20181107" ./row.csv
我试图将输入数据加载到错误的分区,但收到错误:

$ echo "1,3.14,2018-11-07" > row.csv
$ bq load "tmp_elliottb.PartitionedTable\$20181105" ./row.csv
Some rows belong to different partitions rather than destination partition 20181105
然后,我替换了分区的数据:

$ echo "1,3.14,2018-11-07" > row.csv
$ bq load "tmp_elliottb.PartitionedTable\$20181107" ./row.csv
$ echo "2,0.11,2018-11-07" > row.csv
$ bq load --replace "tmp_elliottb.PartitionedTable\$20181107" ./row.csv
是的,可以使用
MERGE
替换分区表分区的数据,但也可以使用加载作业

因为他们不允许一个人使用$decorator

但它们确实如此——当您加载到基于列的分区表中时,也可以使用
表名$YYYYMMDD

$ bq query --use_legacy_sql=false "CREATE TABLE tmp_elliottb.PartitionedTable (x INT64, y NUMERIC, date DATE) PARTITION BY date"
然后我加载到一个特定的分区:

$ echo "1,3.14,2018-11-07" > row.csv
$ bq load "tmp_elliottb.PartitionedTable\$20181107" ./row.csv
$ echo "2,0.11,2018-11-07" > row.csv
$ bq load --replace "tmp_elliottb.PartitionedTable\$20181107" ./row.csv
我试图将输入数据加载到错误的分区,但收到错误:

$ echo "1,3.14,2018-11-07" > row.csv
$ bq load "tmp_elliottb.PartitionedTable\$20181105" ./row.csv
Some rows belong to different partitions rather than destination partition 20181105
然后,我替换了分区的数据:

$ echo "1,3.14,2018-11-07" > row.csv
$ bq load "tmp_elliottb.PartitionedTable\$20181107" ./row.csv
$ echo "2,0.11,2018-11-07" > row.csv
$ bq load --replace "tmp_elliottb.PartitionedTable\$20181107" ./row.csv

是的,您可以使用
MERGE
作为替换分区表分区数据的一种方式,但您也可以使用加载作业。

谢谢!我回头看了一下为什么我认为这是不可能的,这是因为我从Airflow收到了一条错误消息(在本例中,它不能准确反映BigQuery API)。对于我的用例,此解决方案比DML好得多,因为它处理模式随时间增加而更新的情况(因此不一致),我似乎无法处理DML,因为它要求我明确列出要插入到表中的所有列。@conradlee那么,您是如何使用Airflow操作符用新数据更新BQ表的?我有一个场景,我的现有表被一个日期列分区,而我的增量加载会为该表带来数据在过去三天中,尝试加载数据失败,出现错误
异常:BigQuery作业失败。最终错误为:{'reason':'invalid','message':'某些行属于不同的分区,而不是目标分区20191202'}
非常感谢您在这方面提供的帮助。您好,您能为几个分区添加将在分区表中执行删除和插入操作的DML吗?谢谢!我返回并查看了我认为这不可能的原因,这是因为我收到了来自Airflow的错误消息(在本例中,它不能准确地反映BigQueryAPI)。对于我的用例,该解决方案比DML好得多,因为它处理模式随着时间的推移而不断更新(因此不一致)的情况,我似乎无法处理DML,因为它要求我明确列出要插入到表中的所有列。@conradlee那么,您是如何使用Airflow操作符用新数据更新BQ表的?我有一个场景,我的现有表被一个日期列分区,而我的增量加载会为该表带来数据在过去三天中,尝试加载数据失败,出现错误
异常:BigQuery作业失败。最终错误为:{'reason':'invalid','message':'某些行属于不同的分区,而不是目标分区20191202'}
非常感谢您在这方面提供的任何帮助。您是否可以为多个分区添加将在分区表中执行删除和插入操作的DML?