使用Python/Google Sheets API的BatchUpdate批量删行遇JSON错误
问题解决及代码优化
首先,你遇到的JSON错误是字典键名写错了——代码里写的"requests:"多了个冒号,Google Sheets API要求的键名是"requests",这就是导致"unknown name"错误的直接原因。
另外,你的代码还有个效率问题:现在是每找到一行要删除的就发一次batchUpdate请求,频繁调用API不仅慢,还容易触发配额限制。应该先把所有删除请求收集起来,最后一次性发送。
修正后的代码
rowsDeleted = 0 deleteRequests = [] # 统一收集所有删除请求 for i, rowF in enumerate(filterValues): currentDiv = rowF[8] if division[1] != currentDiv: # 计算当前要删除行的索引(因为已经删了rowsDeleted行,所以要调整) deleteIndex = i - rowsDeleted deleteRequests.append({ 'deleteDimension': { 'sheetId': dupeId, 'dimension': "ROWS", 'startIndex': deleteIndex, 'endIndex': deleteIndex + 1 # 注意:endIndex是开区间,所以要+1才能删除这一行 } }) rowsDeleted += 1 # 所有请求收集完成后,一次性发送 if deleteRequests: try: body = {"requests": deleteRequests} request = service.spreadsheets().batchUpdate(spreadsheetId=meritMain, body=body) response = request.execute() print(f"成功删除{rowsDeleted}行数据") print(response) except HttpError as err: print(err)
关键修正点说明
- 键名修正:把
"requests:"改成"requests",符合Google Sheets API的请求格式要求 - 批量请求收集:把删除请求移到循环外统一收集,最后一次发送,大幅提升效率
- 索引修正:原代码里
startIndex和endIndex设为同一个值,而Google Sheets API的deleteDimension中endIndex是开区间,必须设为deleteIndex + 1才能正确删除单行 - 空请求判断:增加
if deleteRequests:判断,避免没有要删除的行时发送无效请求
额外优化建议
如果数据量很大,从后往前删除行可以不用维护rowsDeleted变量,因为删除后面的行不会影响前面行的索引,示例代码如下:
# 先收集所有需要删除的原始行索引 rows_to_delete = [i for i, rowF in enumerate(filterValues) if division[1] != rowF[8]] # 从大到小排序,实现从后往前删 rows_to_delete.sort(reverse=True) deleteRequests = [] for idx in rows_to_delete: deleteRequests.append({ 'deleteDimension': { 'sheetId': dupeId, 'dimension': "ROWS", 'startIndex': idx, 'endIndex': idx + 1 } }) # 后续发送请求逻辑同上
内容的提问来源于stack exchange,提问作者d3newbie
相关产品推荐
相关产品推荐

