Registry / workflow / APScheduler

APScheduler

JSON →
library3.11.3pypypi✓ verified 24d ago

Advanced Python Scheduler — schedule Python functions to run at specified times or intervals. Current stable version is 3.11.2. A completely rewritten 4.x is in pre-release with a different API (apscheduler.Scheduler instead of BackgroundScheduler, etc.) — 4.x is NOT installed by pip install APScheduler. Two concurrent stable lines: use 3.x for production. The 3.x vs 4.x API confusion is the #1 footgun.

pip install APScheduler
INSTALL
IMPORT
SIG · APSCHEDULER
A
APScheduler
workflowpythonv3.11.3
Install
2.6s avg
Import
394ms
Disk
42MB
Pass rate
10/ 10
Env Coverage10 / 10
glibc
3.93.13
musl
3.93.13
Install & Compatibility
Where this runs
tested against v3.11.3 · pip install
no network on importno background threads
Install × environment matrix
Each cell = how many times install + import succeeded across repeated harness runs. Partial = flaky.
glibc = Debian/Ubuntu slim · musl = Alpine Linux
musl
py 3.103.915 runs
installs and imports cleanly · install 0.0s · import 0.418s · 43.8MB
glibc
py 3.103.915 runs
installs and imports cleanly · install 2.6s · import 0.370s · 42MB
42MB installed
● package 42MB
Code
Verified usage

Verified import paths — ran on the pinned version, not inferred.

BackgroundScheduler
from apscheduler.schedulers.background import BackgroundScheduler
from apscheduler.schedulers.background import BackgroundScheduler
CronTrigger
from apscheduler.triggers.cron import CronTrigger
from apscheduler.triggers.cron import CronTrigger
IntervalTrigger
from apscheduler.triggers.interval import IntervalTrigger
from apscheduler.triggers.interval import IntervalTrigger

3.x stable API. BackgroundScheduler runs in a thread. Always call start() and shutdown().

from apscheduler.schedulers.background import BackgroundScheduler from datetime import datetime import time def job_function(): print(f'Job ran at {datetime.now()}') # BackgroundScheduler runs in a daemon thread scheduler = BackgroundScheduler() # Interval trigger scheduler.add_job(job_function, 'interval', seconds=10, id='my_job') # Cron trigger (every day at 9:30am) scheduler.add_job(job_function, 'cron', hour=9, minute=30) # Date trigger (one-off) from datetime import timedelta scheduler.add_job( job_function, 'date', run_date=datetime.now() + timedelta(minutes=1) ) # Must start explicitly scheduler.start() print('Scheduler started. Press Ctrl+C to exit.') try: while True: time.sleep(1) except KeyboardInterrupt: scheduler.shutdown()
Debug
Known issues
breakingAPScheduler 4.x (a complete rewrite) is in pre-release and has a completely different API. pip install APScheduler installs 3.x — NOT 4.x. 4.x docs and tutorials showing from apscheduler import Scheduler will raise ImportError on 3.x installs.
fix
For production: pip install APScheduler installs stable 3.x. For 4.x pre-release: pip install 'APScheduler>=4.0a1'. The 3.x and 4.x APIs are completely incompatible.
affects: 4.x pre-release vs 3.x stable
gotchascheduler.start() must be called explicitly. Creating a scheduler and adding jobs without calling start() does nothing — jobs never run.
fix
Always call scheduler.start() after adding jobs. For Flask/Django: call it in app startup, not module level.
affects: 3.x
gotchaJobs are lost on restart unless a persistent job store (SQLAlchemy, Redis, MongoDB) is configured. The default MemoryJobStore holds jobs only in RAM.
fix
Configure a persistent job store: scheduler = BackgroundScheduler(jobstores={'default': SQLAlchemyJobStore(url='sqlite:///jobs.sqlite')})
affects: 3.x
gotchaRunning multiple processes each with their own scheduler (e.g. gunicorn with multiple workers) causes duplicate job execution. APScheduler 3.x has no inter-process coordination.
fix
Run the scheduler in a single dedicated process. Use a persistent job store with coalesce=True and max_instances=1. Or use a task queue (Celery, RQ) for multi-process environments.
affects: 3.x
gotchaBlockingScheduler blocks the main thread — use it only when the scheduler IS the application. BackgroundScheduler runs in a daemon thread and is suitable for running alongside a web app.
fix
Web apps: use BackgroundScheduler. Standalone scheduler scripts: use BlockingScheduler. Async apps: use AsyncIOScheduler.
affects: 3.x
gotchaAll times are naive (timezone-unaware) unless you configure a timezone. Scheduled jobs may run at wrong times during DST transitions.
fix
Always set timezone: BackgroundScheduler(timezone='UTC') or use pytz: BackgroundScheduler(timezone=pytz.timezone('America/New_York'))
affects: 3.x
Upgrade
Version history
3.11.3latest on PyPI · released Jun 28, 2026
Audit
Dependencies
tzlocal>=2.0requiredRequired for timezone support. Installed automatically.
pytzrequiredRequired for timezone handling. Installed automatically.
sqlalchemy>=1.4optionalRequired for SQLAlchemyJobStore. Install via APScheduler[sqlalchemy].
redisoptionalRequired for RedisJobStore. Install via APScheduler[redis].
Agent activity
113 hits · last 30 days
node
103
Perplexity
1
OpenAI (training)
1
Resources
APScheduler — pip install APScheduler · libregistry