You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Google Apps Script调用Notion API分页查询异常问题求助

解决Notion API分页查询异常问题

问题现象

开发Google Sheet配套的Apps Script时,使用Notion API查询数据库遇到分页异常:

  • 结果少于100条时,首次请求正常
  • 结果超过100条时,分页请求出现以下问题:
    • 第二次请求has_more始终为true,返回100条记录(预期仅剩余15条)
    • 携带filter参数时,重复获取前100条且has_more一直为true
    • 不携带filter参数时,返回100条记录,仅前15条符合过滤条件,后续出现不符合要求的记录

问题原因分析

  1. 分页请求丢失过滤/排序参数:原代码第一次请求后将payload设为null,导致后续请求无过滤条件,返回全量数据的分页结果而非过滤后的结果。
  2. 游标参数传递错误:Notion API要求start_cursor放在请求体中,原代码将其放在UrlFetchApp的options顶层,导致分页游标未被正确识别。
  3. 日期格式不兼容:直接传递Date对象给Notion API,未转换为API可解析的ISO 8601格式字符串。

修正后的代码

function getNotionTaskCompletions () {
  // Setup URLs 
  const url1 = "https://api.notion.com/v1/databases/xxxxxxx/query/";
  const headers = {
    Authorization: "Bearer secret_xxxxxxx",
    "Content-Type": "application/json",
    "Notion-Version": "2022-06-28",
  };
  
  // 计算30天前的日期,转换为ISO 8601格式字符串
  const nowDate = new Date(Date.now());
  const startDate = new Date(nowDate.getTime() - 30*1000*60*60*24).toISOString();

  // 基础请求体,固定过滤和排序规则
  const basePayload = {
    "filter": {
      "and": [
        {"property": "Status",
         "status": {
           "equals": "Done",
         },
        },        
        {"property": "Complete",
         "date": {
             "on_or_after": startDate,
         },
        },
      ]        
    },
    "sorts": [
      {
        "property": "Complete",
        "direction": "ascending",
      }
    ]
  };

  const tName = [];
  const tDate = [];

  let cursor = null;
  let hasMore = true;

  while (hasMore) {
    // 构建当前页请求体:基础参数 + 游标(如果存在)
    const requestPayload = {
      ...basePayload,
      ...(cursor && { start_cursor: cursor })
    };

    const options = {
      "muteHttpExceptions": true,
      "method": "post",
      "headers": headers,
      "payload": JSON.stringify(requestPayload),    
    };  

    const response = UrlFetchApp.fetch(url1, options);
    const json = JSON.parse(response.getContentText());
    
    hasMore = json.has_more;
    cursor = json.next_cursor;

    // 遍历当前页结果
    for (const result of json.results) {
      const taskTitle = result.properties.Task.title[0]?.plain_text || "";
      const completeDate = result.properties.Complete.date?.start.split("T")[0] || "";
      
      tName.push(taskTitle);
      tDate.push(completeDate);
      
      Logger.log(`${taskTitle} - ${completeDate}`);
    }
  }

  // 清空目标区域
  const dSheet = SpreadsheetApp.getActiveSpreadsheet().getSheetByName("data");
  dSheet.getRange("K1:N300").clear({contentsOnly: true});

  // 将数据写入表格
  for (let i = 0; i < tName.length; i++) {
    dSheet.getRange(1 + i, 11).setValue(tName[i]);
    dSheet.getRange(1 + i, 12).setValue(tDate[i]);          
  }
}

关键修改说明

  • 保留完整请求参数:每次分页请求都基于basePayload构建,确保过滤和排序规则始终生效,避免返回非目标数据。
  • 正确传递分页游标:将start_cursor放入请求体中,符合Notion API的参数规范,确保分页逻辑正常运转。
  • 日期格式标准化:将日期转换为ISO 8601字符串,避免API解析错误。
  • 移除冗余校验:由于每次请求都携带过滤条件,返回结果必然符合要求,无需额外判断状态是否为"Done"。
  • 代码优化:使用let/const替代var,用for-of循环简化遍历,添加可选链操作符避免空值报错。

内容的提问来源于stack exchange,提问作者Rich Bair

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.11 01:32:23