BigQuery通常可以很好地加载Avro数据,但是“bq load”在时间戳和使用Avro logicalType属性的其他日期/时间字段方面遇到了很多麻烦。
我想我总是可以通过将数据加载到临时字段并使用查询到CAST或将它们转换为其他字段来解决这些问题,但这不会扩展或支持模式演变或流式传输。使用定义良好的模式在Avro中生成数据应该避免为不同的消费者再次转换数据的额外步骤。
BigQuery真的与Avro日期和时间不兼容吗? (或者我做的事情是愚蠢的)
或者“bq加载”问题在这里?有没有更好的方法来加载Avro数据?
答案 0 :(得分:5)
更新:现在支持此功能,请点击issuetracker.google.com/35905894了解详情。
正如Hua所说,BigQuery不支持Avro逻辑类型,但是加载带有时间戳的Avro数据的支持方式是使用LONG Avro类型将数据加载到具有TIMESTAMP列的现有BigQuery表中。此外,该值应为EPOCH的微秒(不是秒或毫秒)。例如,下面的Avro文件有一个LONG字段,其值为1408452095000000,表示“2014-08-19 12:41:35”。
Avro文件的架构:
% avro-tools getschema ~/dataset/simple_timestamp.avro
{
"type" : "record",
"name" : "FullName",
"fields" : [ {
"name" : "t",
"type" : "long"
} ]
}
将Avro文件加载到带有Timestamp字段的表的示例:
bq mk --schema t:TIMESTAMP -t vimota.simple_timestamp
bq load --source_format=AVRO vimota.simple_timestamp ~/dataset/simple_timestamp.avro
bq head vimota.simple_timestamp:
+---------------------+
| t |
+---------------------+
| 2014-08-19 12:41:35 |
+---------------------+
答案 1 :(得分:3)
现在可以为所有BigQuery用户公开了解Avro Logical Types的原生理解。有关详细信息,请参阅此处的文档页面:https://cloud.google.com/bigquery/docs/loading-data-cloud-storage-avro#logical_types
答案 2 :(得分:2)
我在PostgreSQL表中有TIMESTAMP列的数据。在遵循https://github.com/spotify/spark-bigquery/issues/19的评论意见后,我能够通过Avro将其导入BigQuery。
在Kotlin中使用PostgreSQL JDBC库,我重新计算了时间戳into BigQuery internal format(自Unix纪元开始以来的微秒)
(object as java.sql.Timestamp).time * 1000
并将其放入我的Schema.Type.LONG
类型的avro记录中。
然后我created a schema file for my data in JSON我给了#34;时间戳"的列类型。
[
{"name": "job", "type": "string", "mode": "required"},
...
{"name": "began", "type": "timestamp", "mode": "required"},
...
]
(参见开始字段)
最后,我使用
将其导入BigQuerybq mk test.test2 dataset.avro schema.json
结果是
$ bq head test.test2
+------+----+----------+---------------------+---------+-----------+
| job | id | duration | began | status | node_name |
+------+----+----------+---------------------+---------+-----------+
| job1 | 1 | 0.0 | 2012-04-01 00:00:00 | aStatus | aNodeName |
| job2 | 1 | 0.0 | 2020-02-02 00:02:02 | aStatus | aNodeName |
+------+----+----------+---------------------+---------+-----------+
Web UI不允许为Avro文件指定架构,但CLI客户端和API会这样做。
我仍然遇到的唯一问题是处理时区。但这对Avro来说不是问题。
答案 3 :(得分:1)
我们遇到了同样的问题并解决了。用于将日期数据导入现有的 DATE 类型的 BQ 表字段的 Avro 架构如下。日期值的整数值必须是自纪元以来的天数(不是秒)。请注意使用嵌套格式的架构类型定义的样式。
bq load --source_format AVRO --use_avro_logical_types s1.avro_date gs://bucket_name/bq_date_int_logical_nested.avro
echo "select * from s1.avro_date" | bq query
Waiting on bqjob_r1433d5cfa5eb9a89_00000176f3182f03_1 ... (0s) Current status: DONE
+------------+
| day |
+------------+
| 2021-01-12 |
+------------+
使用的架构:
{
"type" : "record",
"name" : "bq_date",
"namespace" : "my.namespace",
"fields" : [{
"name" : "day",
"type" : {
"type" : "int",
"logicalType" : "date"
}
}
]
}
FWIW:我们测试了使用 Avro Python 1.10.1 和 Java 库创建的测试文件。