urlcap

Schedules

Schedule recurring HTTP checks without running a cron server

Updated · Related endpoint: /api/v1/schedules

Try this in 60 seconds. 5 free requests with no account, then 1,000/month on the free tier. Get a free API key →

The problem: small recurring HTTP checks shouldn't need a cron server

You want to hit a URL every fifteen minutes and look at the response. Maybe it's a homepage uptime check. Maybe it's a "is the new build's /version endpoint returning the expected hash". Maybe it's a daily compliance snapshot — fetch a regulator's page, store the body, prove later it didn't change without anyone noticing.

The traditional way is a cron entry on a server somewhere. That works, but you now own a tiny piece of infrastructure: a host, a cron file, an outbound network path, logs, a place to store the response, retries, alerting when cron didn't run. For something that should be one line, that's a lot of incidental complexity.

/api/v1/schedules takes the same idea — "run this HTTP request on a cron expression" — and moves it to urlcap's side. You POST the schedule once; we run it; the result of every run is stored under your account and queryable via GET /schedules/{id}/runs.

Who this is for

Step 1 — create a recurring schedule

The smallest body says "run a capture against this URL on this cron expression". The cron syntax is the classic 5-field format (minute hour day-of-month month day-of-week); macros like @hourly, @daily, @weekly also work.

15-min health check · curl
curl -s https://urlcap.com/api/v1/schedules \
  -H "Authorization: Bearer $URLCAP_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "name":     "prod homepage health",
    "cron":     "*/15 * * * *",
    "timezone": "Europe/London",
    "capture":  { "url": "https://acme.io/", "method": "GET" }
  }'

Response (truncated):

201 Created
{
  "data": {
    "schedule": {
      "id":         "0f4cae12-…-uuid",
      "kind":       "capture",
      "name":       "prod homepage health",
      "cron":       "*/15 * * * *",
      "timezone":   "Europe/London",
      "status":     "active",
      "nextRunAt":  "2026-05-14T12:45:00Z",
      "runs":       0,
      "createdAt":  "2026-05-14T12:30:00Z",
      "capture":    { "url": "https://acme.io/", "method": "GET" }
    }
  }
}

Step 2 (optional) — one-shot future runs

For a single future run instead of a cron — say, "fetch the report at 09:00 on 1 June" — send runAt instead of cron:

one-shot
curl -s https://urlcap.com/api/v1/schedules \
  -H "Authorization: Bearer $URLCAP_KEY" -H "Content-Type: application/json" \
  -d '{
    "name":    "june 1 report fetch",
    "runAt":   "2026-06-01T09:00:00Z",
    "capture": { "url": "https://reports.acme.io/2026-q2" }
  }'

Step 3 — inspect what happened

Every execution writes a row of run history. List them with GET /api/v1/schedules/{id}/runs; fetch one full run (status, headers, body) with GET /api/v1/schedules/{id}/runs/{runNo}.

last 10 runs
curl -s "https://urlcap.com/api/v1/schedules/$SCHEDULE_ID/runs?limit=10" \
  -H "Authorization: Bearer $URLCAP_KEY"

The response lists runNo, startedAt, finishedAt, response status, and a request id you can use to fetch the full capture for that run. Pipe this into whatever alerting you already have — e.g. a Slack message when three consecutive runs return a non-2xx status.

Useful patterns

Uptime & latency tracking

A */5 * * * * schedule against /health gives you 288 data points per day. Even at every-minute resolution (* * * * *) that's 1,440/day — within the Free tier's monthly quota for a single check, or comfortably on Developer if you have many.

Content-change detection

Use an extract schedule instead of a capture schedule to pull a specific value from the page (a CSS selector, an XPath, a JSONPath). Diff the value across runs; alert on the change. Example use cases: tracking a third-party pricing page, a competitor's status page, a regulator's policy section.

Compliance snapshots

A nightly @daily capture against a third-party legal/policy page gives you a tamper-evident timeline of "what that page said on each day". Each run's full response body is stored under your account; auditors can fetch any historical run by runNo.

Combine with datasets

Schedule an extract that runs against every URL in a dataset — useful for periodically refreshing a list of partner endpoints, or building a small crawler that always operates on a curated allowlist.

Production notes

When urlcap is the right tool — and when it isn't

Use caseBest fit
A handful of recurring HTTP checks, kept under one API keyurlcap schedules
A few hundred uptime probes from global regions, with SMS / PagerDutyUptimeRobot, Pingdom, Better Uptime
Status-page integration for customersStatuspage, Instatus
Heavy ETL on cron with retry semantics, DAGs, branchingAirflow, Dagster, GitHub Actions cron
A recurring HTTP capture / extract you'd otherwise put in a 5-line cron fileurlcap schedules

The sweet spot is the small recurring job that's not big enough to deserve its own infrastructure but is annoying to maintain by hand. If you find yourself wanting 50 regions, multi-region failover, or DAG orchestration, urlcap is the wrong tool.

Pricing & limits

Each run that the scheduler executes counts as one request unit against your monthly quota. Free plan: 1,000 runs/month. Developer: 50,000. Startup: 250,000. Business: unlimited monthly quota, fair-use per-second rate limits apply. See /pricing.

Create a free API key and schedule your first check.

No card. 1,000 runs / month on the free tier.