我应该为每一行插入调用 BigQuery 还是应该插入一个批量?

Posted

技术标签:

【中文标题】我应该为每一行插入调用 BigQuery 还是应该插入一个批量?【英文标题】:Should I call BigQuery for every row insert or should I insert a bulk? 【发布时间】:2019-05-29 18:12:47 【问题描述】:

我有一个 NodeJs 服务(基于 Express 构建),每天有 1 亿个请求,并且对于每个请求,都会向 BigQuery 发送一个新数据行。 继续单独发送行还是我应该收集行并每隔 X 秒/分钟将它们作为批量发送到 BigQuery 是否更好,性能明智? (调用是异步完成的)

我的 BigQuery 存储库类如下所示:(在 Express 服务启动时,存储库通过调用 .init() 进行初始化,并为每一行插入服务调用 .add())

function BQRepository() 


BQRepository.prototype.init = async function() 
    this.bigQueryClient = new BigQuery( projectId: ..., keyFilename: ... );    


BQRepository.prototype.add = async function(tableName, obj) 
    this.bigQueryClient
        .dataset(...)
        .table(tableName)
        .insert(obj)
        .then(() => 
          logger.debug(`object added`)
        )
        .catch(err => 
                    logger.error('error occurred')
        );


var bqRepo = new BQRepository()
module.exports = bqRepo;

【问题讨论】:

您在寻找什么性能优化?消费者;节点; BQ、服务器内存/CPU? 起初我的目标是服务器 CPU 负载,但我认为所有性能标准都很有趣 【参考方案1】:

我不确定问题中是否有足够的信息来提供一个简单明了的答案,因为您当前的每个请求方法的交易似乎没有达到任何硬​​性限制。如果服务在每个批量事务之间失败,则收集执行批量事务的请求可能有助于限制网络 I/O,但可能会丢失事务。我建议您进行性能测试,以直接比较每种方法并了解它们对您的用例的优缺点。

您忽略的最后一件事可能是成本,具体取决于单个行的大小。基于BigQuery cost projections:

使用 1 KB 的最小大小计算单个行

根据您对象的大小,如果您的行数足够小,您可能会被多收费,除非您将它们捆绑成批量交易。

【讨论】:

以上是关于我应该为每一行插入调用 BigQuery 还是应该插入一个批量?的主要内容,如果未能解决你的问题,请参考以下文章

当对基于声明的模型使用多值插入时,不会为每一行单独调用 Python 端默认值

我应该为每一行日志使用 try-with-resources 语句吗?

insertRowsAtIndexPaths 为每一行调用 cellForRowAtIndexPath

在 C# 中插入具有重复记录列的 BigQuery 行

为啥不应该在删除/插入行的方法上调用 reloadData

大查询 - 仅在列值不存在时插入