Greenhouse, Lever & Ashby Jobs Scraper API
Pricing
$1.00 / 1,000 job normalizeds
Greenhouse, Lever & Ashby Jobs Scraper API
Normalize public Greenhouse, Lever, and Ashby jobs into one dataset. Detect official career URLs and optionally emit only new postings across scheduled runs.
Pricing
$1.00 / 1,000 job normalizeds
Rating
0.0
(0)
Developer
Kunteper Koyu
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
0
Monthly active users
15 hours ago
Last modified
Categories
Share
Fetch published job postings from official public Greenhouse, Lever, and Ashby endpoints and normalize them into one stable schema. Build job boards, hiring-signal datasets, market research, alerts, and recruiting automations without maintaining three provider-specific integrations.
What you get
- company, title, primary and secondary locations, department, and team
- employment type, workplace type, and remote status when available
- plain-text and HTML descriptions
- canonical job and application URLs
- compensation when the provider exposes it
- publication and update timestamps
- deterministic SHA-256 fingerprints for change detection
- careers-URL auto-detection for supported provider URL formats
- persistent
newOnlymode for scheduled monitors - isolated board errors, so one invalid board does not discard successful results
Common use cases
- power a niche job board or searchable jobs API
- monitor target companies for hiring and expansion signals
- create role, keyword, location, and remote-job alerts
- normalize jobs before analytics, enrichment, or RAG ingestion
- track new and changed postings across multiple ATS providers
Quick start
- Find the board token in the company's public careers URL.
- Add the provider, board name, and optional company display name.
- Add keyword, location, remote, or publication-date filters if needed.
- Run the Actor and open the normalized dataset.
{"boards": [{"provider": "greenhouse","boardName": "anthropic","companyName": "Anthropic"},{"provider": "lever","boardName": "leverdemo","companyName": "Lever","region": "global"},{"provider": "ashby","boardName": "Ashby","companyName": "Ashby"}],"searchTerms": ["engineer"],"locations": ["remote", "New York"],"remoteOnly": false,"includeDescription": true,"includeCompensation": true,"publishedAfter": "2026-07-01","maxJobsPerBoard": 1000,"concurrency": 5,"timeoutSeconds": 30}
Lever supports global and eu regions. Board names are the public token or site name in the provider's careers URL.
Alternatively, paste official hosted careers URLs and let the Actor identify the provider and board without crawling the page:
{"careerUrls": ["https://boards.greenhouse.io/example","https://jobs.eu.lever.co/example","https://jobs.ashbyhq.com/example"],"newOnly": true,"stateStoreName": "my-daily-job-monitor"}
Auto-detection is deliberately limited to boards.greenhouse.io,
job-boards.greenhouse.io, jobs.lever.co, jobs.eu.lever.co, and
jobs.ashbyhq.com. It parses the URL locally and calls the provider's public
JSON API; it does not scrape arbitrary company careers domains or follow
redirects. For a custom careers domain, use its official hosted ATS link or
enter the provider and board token under boards.
New-jobs-only scheduled runs
Set newOnly to true to persist stable hashes of provider, board, and source
job ID in the named stateStoreName. The first run emits all matching jobs;
later runs using the same store emit and charge only for previously unseen job
IDs. Edits to a known posting do not make it new. Use a separate store name for
each independent monitor and avoid concurrent runs against the same store,
because key-value-store updates are not transactional. State retains the most
recent 100,000 job identities. The default newOnly: false preserves the
original behavior.
Example result
{"provider": "greenhouse","boardName": "anthropic","companyName": "Anthropic","sourceJobId": "4461450008","title": "Account Executive, AI Native","location": "San Francisco, CA | New York City, NY","secondaryLocations": [],"remote": false,"jobUrl": "https://job-boards.greenhouse.io/anthropic/jobs/4461450008","publishedAt": "2024-12-20T13:53:38-05:00","updatedAt": "2026-06-08T20:49:32-04:00","fingerprint": "cb3e2724e0fde508046d496236f32f598457dc566625918c48655cc80e836697","retrievedAt": "2026-07-06T17:33:19.395Z"}
Run by API
Set APIFY_TOKEN in your environment and keep it out of source control.
cURL
curl -X POST \"https://api.apify.com/v2/acts/rtworule~public-ats-job-feed-normalizer/run-sync-get-dataset-items?token=$APIFY_TOKEN" \-H "Content-Type: application/json" \-d '{"boards":[{"provider":"greenhouse","boardName":"anthropic","companyName":"Anthropic"}],"remoteOnly":true,"maxJobsPerBoard":100}'
JavaScript
import { ApifyClient } from 'apify-client';const client = new ApifyClient({ token: process.env.APIFY_TOKEN });const run = await client.actor('rtworule/public-ats-job-feed-normalizer').call({boards: [{ provider: 'greenhouse', boardName: 'anthropic', companyName: 'Anthropic' }],remoteOnly: true,maxJobsPerBoard: 100,});const { items } = await client.dataset(run.defaultDatasetId).listItems();console.log(items);
Python
import osfrom apify_client import ApifyClientclient = ApifyClient(os.environ["APIFY_TOKEN"])run = client.actor("rtworule/public-ats-job-feed-normalizer").call(run_input={"boards": [{"provider": "greenhouse","boardName": "anthropic","companyName": "Anthropic",}],"remoteOnly": True,"maxJobsPerBoard": 100,})items = client.dataset(run["defaultDatasetId"]).list_items().itemsprint(items)
Pricing
This Actor uses pay per event. A job-normalized event costs $0.001 per stored job: 100 delivered jobs cost $0.10 and 1,000 cost $1.00 in event charges. Apify applies a $0.01 minimum run charge. Filters, per-board limits, and newOnly mode help control output; the Actor stops storing results when the run's maximum total charge is reached. In newOnly mode, remembered postings are not emitted or charged as result events.
Integrations and automation
- schedule with
newOnly: trueto receive and pay for only newly discovered jobs - compare the output
fingerprintseparately when you want to detect edits to known jobs - send matching jobs to Slack, email, Make, Zapier, n8n, or a webhook
- load normalized jobs into a database, search engine, BI tool, or vector store
- export CSV/XLSX to Sheets for research and editorial review
- use
publishedAfter, search terms, and locations to keep recurring runs focused
FAQ and troubleshooting
Is this scraping private candidate or recruiting data? No. It reads only public job-posting endpoints and does not access candidates, applications, internal postings, or authenticated recruiter systems.
Where do I find the board name? It is the company-specific token in the public Greenhouse, Lever, or Ashby careers URL—not necessarily the company's display name.
Why is a job or field missing? Filters may exclude it, the provider may omit the field, or the posting may have been removed. The Actor does not invent missing source data.
How do I avoid duplicate alerts? Enable newOnly and reuse the same
stateStoreName on every scheduled run. The Actor then suppresses previously
seen job IDs before charging or writing output. Keep newOnly disabled if you
want a full snapshot and compare the output fingerprint in your destination
to detect changed postings.
Why did one board fail while the run succeeded? Boards are isolated. Inspect the BOARD_ERRORS key-value-store record for an invalid token, provider response, timeout, or other board-specific error.
Data sources, responsible use, and limitations
The Actor uses public posting endpoints:
- Greenhouse Job Board API:
https://boards-api.greenhouse.io/v1/boards/{board}/jobs - Lever Postings API:
https://api.lever.co/v0/postings/{site} - Ashby Job Postings API:
https://api.ashbyhq.com/posting-api/job-board/{board}
Provider schemas, availability, and job content can change. Compensation, remote status, and timestamps are returned only when the source exposes enough information. Users remain responsible for their downstream use, retention, applicable terms, and compliance.
For a reproducible issue, open an issue from the Actor page with the run ID, provider, public board name, and expected behavior. Never include credentials, candidate data, or other sensitive information.