Java - 一次一行插入google Big Query?

时间:2018-05-08 16:49:12

标签: google-bigquery

我正在创建一个应用程序,每次用户点击文章时,我都需要捕获文章数据和用户数据,以计算每篇文章的覆盖面,并能够对到达的数据进行分析。

我的应用程序在App Engine上。

当我检查BQ插入的文档时,大多数指向以Jobs或Streams形式的批量插入。

问题: 每次启动用户操作时,一次插入一行大查询是一种好习惯吗?如果是这样,你能指点我一些Java代码来有效地做到这一点吗?

2 个答案:

答案 0 :(得分:2)

加载作业和DML查询的数量有限制(每天1,000个),因此您需要将streaming inserts用于此类应用程序。请注意,流式插入不同于从Java流加载数据。

TableId tableId = TableId.of(datasetName, tableName);
// Values of the row to insert
Map<String, Object> rowContent = new HashMap<>();
rowContent.put("booleanField", true);
// Bytes are passed in base64
rowContent.put("bytesField", "Cg0NDg0="); // 0xA, 0xD, 0xD, 0xE, 0xD in base64
// Records are passed as a map
Map<String, Object> recordsContent = new HashMap<>();
recordsContent.put("stringField", "Hello, World!");
rowContent.put("recordField", recordsContent);
InsertAllResponse response =
    bigquery.insertAll(
        InsertAllRequest.newBuilder(tableId)
            .addRow("rowId", rowContent)
            // More rows can be added in the same RPC by invoking .addRow() on the builder
            .build());
if (response.hasErrors()) {
  // If any of the insertions failed, this lets you inspect the errors
  for (Entry<Long, List<BigQueryError>> entry : response.getInsertErrors().entrySet()) {
    // inspect row error
  }
}

(来自https://cloud.google.com/bigquery/streaming-data-into-bigquery#bigquery-stream-data-java的例子)

特别注意失败的插入总是抛出异常。您还必须检查响应对象是否有错误。

  

每次启动用户操作时,每次一行插入一行是一个好习惯吗?

是的,将事件流传输到BigQuery进行分析是非常典型的。如果将多个事件缓冲到与BigQuery相同的流插入请求中,您将获得更好的性能,但一次肯定支持一行。

答案 1 :(得分:0)

Google示例的简化版本。

    Map<String, Object> row1Data = new HashMap<>();
    row1Data.put("booleanField", true);
    row1Data.put("stringField", "myString"); 

    Map<String, Object> row2Data = new HashMap<>();
    row2Data.put("booleanField", false);
    row2Data.put("stringField", "myOtherString"); 

    TableId tableId = TableId.of("myDatasetName", "myTableName");
    InsertAllResponse response =
            bigQuery.insertAll(
                    InsertAllRequest.newBuilder(tableId)
                            .addRow("row1Id", row1Data)
                            .addRow("row2Id", row2Data)
                            .build());

    if (response.hasErrors()) {
        // If any of the insertions failed, this lets you inspect the errors
        for (Map.Entry<Long, List<BigQueryError>> entry : response.getInsertErrors().entrySet()) {
            // inspect row error
        }
    }