更新 BigQuery 架构/在 Java 中添加新列
Posted
技术标签:
【中文标题】更新 BigQuery 架构/在 Java 中添加新列【英文标题】:Update BigQuery Schema / Add New Column in Java 【发布时间】:2018-10-31 16:08:08 【问题描述】:我需要通过 Java 更新 BigQuery 表架构。更改将是附加的(仅添加新列)。
我正在努力寻找实现这一目标的方法。在 Python 中可能是这样的:
table_ref = client.dataset(dataset_id).table(table_id)
table = client.get_table(table_ref) # API request
original_schema = table.schema
new_schema = original_schema[:] # creates a copy of the schema
new_schema.append(bigquery.SchemaField('phone', 'STRING'))
table.schema = new_schema
table = client.update_table(table, ['schema']) # API request
在页面https://cloud.google.com/bigquery/docs/managing-table-schemas 上,声明使用补丁端点来执行此任务。
提出了一个改进补丁 API 的问题,但我不知道结果https://github.com/googleapis/google-cloud-java/issues/1564
这是补丁类文档的链接:https://developers.google.com/resources/api-libraries/documentation/bigquery/v2/java/latest/com/google/api/services/bigquery/Bigquery.Tables.Patch.html#set-java.lang.String-java.lang.Object-
任何帮助将不胜感激。谢谢
【问题讨论】:
【参考方案1】:Java 中的想法与您分享的 Python 示例中的想法相同,即获取当前模式并向其中添加新列。您可以使用我准备的 sn-p 来实现这一点,您可以在下面看到:
// Instantiate the BQ client
BigQuery bigquery = BigQueryOptions.getDefaultInstance().getService();
// Get the table, schema and fields from the already-existing table
Table table = bigquery.getTable(TableId.of("PROJECT_ID", "DATASET", "TABLE"));
Schema schema = table.getDefinition().getSchema();
FieldList fields = schema.getFields();
// Create the new field
Field newField = Field.of("column2", LegacySQLTypeName.STRING);
// Create a new schema adding the current fields, plus the new one
List<Field> field_list = new ArrayList<Field>();
for (Field f : fields)
field_list.add(f);
field_list.add(newField);
Schema newSchema = Schema.of(field_list);
// Update the table with the new schema
Table updatedTable = table.toBuilder().setDefinition(StandardTableDefinition.of(newSchema)).build().update();
此代码正在使用com.google.cloud.bigquery
包(请参阅其documentation here)。然后,它按照tables documentation 中的示例指定架构定义,最后更新它。
【讨论】:
非常感谢,会回复您是否有效,但看起来正是我需要的 很高兴能为您提供帮助!毕竟,如果答案对您有用,请考虑accepting and/or upvoting,以便社区看到它解决了您的问题。谢谢! 虽然这确实可以满足我的需要,但不幸的是,我使用的是不允许 com.google.cloud.bigquery 包的 Apache Beam 框架。相反,它使用了自己的梁包和另一个谷歌包:com.google.api.services.bigquery 我再次努力寻找通过这个包的方法,你碰巧知道吗?再次感谢 !这是***文档developers.google.com/resources/api-libraries/documentation/… 的链接 嗨@SimSimmer;谢谢你接受我的回答。我同意这适用于 BigQuery Java 客户端库,但不一定适用于 Apache Beam 环境。无论如何,如果这是一个完全不同的主题/问题,我建议您发布一个新问题,以便将其视为不同的问题,您可以添加适当的 Dataflow/Apache Beam 标签。 另外,为了让您可以开始处理这个单独的问题,我不确定是否有可能实现我的回答所建议的内容。相反,您可能必须使用 BigQuery 加载作业动态添加列,方法是使用新列更改架构,如 the documentation 中所述。【参考方案2】:我还设法通过其他 Google BigQuery 包做到了:
HttpTransport transport = new NetHttpTransport();
JsonFactory jsonFactory = new JacksonFactory();
GoogleCredential credential;
try
credential = GoogleCredential.getApplicationDefault(transport,
jsonFactory);
catch (IOException e)
throw new RuntimeException(e);
if (credential.createScopedRequired())
credential = credential.createScoped(BigqueryScopes.all());
Bigquery.Tables bqTables = new Bigquery.Builder(transport, jsonFactory, credential).build().tables();
Bigquery.Tables.Get bqTableGet = bqTables.get(this.project, this.dataset, this.tablePrefix + strDate);
Table bqTable = bqTableGet.execute();
bqTable.setSchema(this.schema);
Bigquery.Tables.Patch bqTablePatch = bqTables.patch(this.project, this.dataset, this.tablePrefix + strDate, bqTable);
bqTablePatch.execute();
【讨论】:
以上是关于更新 BigQuery 架构/在 Java 中添加新列的主要内容,如果未能解决你的问题,请参考以下文章
使用 Python API 使用 RECORD 字段更新 BigQuery 架构
Bigquery:我们应该在模式更新后等待多长时间才能流式传输数据?
使用流式 API 更新新列后无法向 BigQuery 表插入新值