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

如何基于系统时间让Python Schedule每30分钟精准执行定时任务

延迟根因
  • 你当前用的schedule.every(30).minutes.do(crawl)默认规则是:上一次任务执行结束后才开始计算30分钟间隔,爬虫本身的执行耗时会被完全算入间隔周期,跑的次数越多,耗时累积的延迟越高。
  • 循环里固定time.sleep(1)的轮询逻辑最多会带来1秒的检查误差,叠加操作系统进程调度的时间偏差,长期运行后误差会持续累积,你遇到的每次攒出1分钟延迟就是这两个因素共同导致的。
跨系统精准30分钟运行方案

最稳定、无累积误差的实现方式是直接对齐操作系统的系统时钟,固定在每小时的0分、30分触发任务,完全不依赖相对时间计时,Mac/Windows/Linux全平台通用,只要系统时间同步准确就不会飘。
完整可运行代码如下:

import time
import schedule
from datetime import datetime

# 任务运行锁,避免单次爬虫执行超过30分钟时出现重复启动
crawl_is_running = False

def crawl():
    global crawl_is_running
    if crawl_is_running:
        print(f"{datetime.now()} 上轮爬虫未执行完成,跳过本次触发")
        return
    crawl_is_running = True
    try:
        # 替换成你自己的爬虫逻辑
        print(f"{datetime.now()} 爬虫开始执行")
    finally:
        crawl_is_running = False

# 绑定每小时0分、30分两个时间点触发,完全对齐系统时钟
schedule.every().hour.at(":00").do(crawl)
schedule.every().hour.at(":30").do(crawl)

if __name__ == "__main__":
    while True:
        schedule.run_pending()
        # 不固定sleep1秒,直接计算距离下次任务的等待时间,既减少空转也消除轮询误差
        next_run_time = schedule.next_run()
        wait_seconds = (next_run_time - datetime.now()).total_seconds()
        # 留0.1秒缓冲,避免系统调度延迟导致错过触发点
        time.sleep(max(wait_seconds - 0.1, 0))

方案说明

  • 触发逻辑完全绑定系统时钟,不存在累积误差:哪怕某次爬虫执行耗时5分钟,下一次任务依然会对齐最近的0分/30分点触发
  • 动态计算sleep时长替代固定1秒休眠,把轮询误差控制在0.1秒以内,同时减少无意义的CPU空转
  • 内置运行锁,避免任务重入导致的重复爬取问题

如果你不需要对齐整半点,要求严格以上一次任务启动时间为起点间隔30分钟运行,可以在crawl函数第一行手动调用schedule.clear()重新注册下一次30分钟后的任务,把任务执行耗时排除在间隔计算之外即可。

内容的提问来源于stack exchange,提问作者joonoo noo

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.02 05:36:35