Scheduling
Barca can act as a plain task scheduler: decorate a function with a cron
expression and leave barca serve running. No external cron, no DSL — the
scheduler is built into the server and on by default.
Run a script every 10 minutes
Section titled “Run a script every 10 minutes”from barca import task, Schedule
@task(freshness=Schedule("*/10 * * * *"))def refresh(): # ...do the work: hit an API, rebuild a file, send a report... print("ran at", __import__("datetime").datetime.now())barca serve job.pyThat’s the whole setup. barca serve parses the file, finds every scheduled
definition, and fires each one on its cron tick. refresh now runs every ten
minutes for as long as the server is up:
[barca] serving on http://127.0.0.1:8274 (1 file)[barca] scheduling 1 asset: job.py:refresh — */10 * * * * (next 2026-07-16 12:30)@task is the right decorator when the point is the side effect — a task always
re-runs when its tick fires. Use @asset(freshness=Schedule(...)) instead when
the function produces data you want kept fresh; scheduled assets fire the same
way but are cache-aware.
Cron reference
Section titled “Cron reference”Barca uses standard 5-field cron (minute hour day-of-month month day-of-week),
evaluated in the machine’s local time by default:
| Cron | Fires |
|---|---|
*/10 * * * * |
every 10 minutes |
0 * * * * |
every hour, on the hour |
0 5 * * * |
every day at 05:00 |
0 9 * * 1 |
09:00 every Monday |
0 0 1 * * |
midnight on the 1st each month |
The finest granularity is one minute — seconds are not supported.
Keeping it running
Section titled “Keeping it running”The scheduler only fires while barca serve is alive, so run it under a process
supervisor for anything long-lived. A minimal systemd unit:
[Service]ExecStart=/usr/local/bin/barca serve /srv/pipelines/job.pyRestart=alwaysWorkingDirectory=/srv/pipelines
[Install]WantedBy=multi-user.targetIn a container, barca serve job.py is a fine foreground entrypoint. Barca
persists each job’s last fire time, so a missed tick during a restart fires
once on catch-up rather than being lost (see caveats).
Inspecting the schedule
Section titled “Inspecting the schedule”Without starting a server, list definitions and their next fire time:
barca list job.pyNAME KIND FRESHNESS NEXT FIRE DEPS------------------------------------------------------------job.py:refresh task cron: */10 * * * * 2026-07-16 12:30 -While the server is running, GET /schedule returns live status (next fire,
last run id, last status) for each job. See the
Server API for the response shape.
Caveats
Section titled “Caveats”- Timezone — cron is local time by default. Pass
--timezone utcor an IANA name (--timezone America/New_York) to change it. - Catch-up — if a tick elapsed while the daemon was down, the job fires once on restart to catch up. Ticks missed during a long outage are not replayed one-for-one, and brand-new jobs are anchored to “now” (no first-launch stampede).
- No self-overlap — if a job’s previous run is still going when the next tick arrives, that tick is skipped.
- Disable it —
barca serve --no-schedule job.pyserves the HTTP API without firing anything on a clock.
For the full semantics — how staleness, sensors, and reconciliation interact with schedules — see Schedule-Driven Reconciliation.