Glassdoor API & Scraper
The Glassdoor API returns company profiles, ratings, reviews, interview reports, salary bands and job listings as clean JSON.
🤖 Using an AI assistant? Copy this link into ChatGPT / Claude / Cursor — it reads every endpoint and parameter instantly and tells you if this API fits your use case.
Start at employer/search to turn a company name into an employer_id, then call employer/detail for firmographics and the full ratings breakdown, employer/reviews for what employees say, employer/interviews for the hiring process, employer/salaries for P10-P90 pay bands by job title, and employer/jobs for open US roles - each with a harvest variant for bulk collection. It reads only the public, signed-out Glassdoor surface: no login, no scraper to maintain. One ReefAPI key, one shared credit pool, the standard envelope.
What each Glassdoor action returned on 2026-09-24, and how deep the public surface goes
Every action needs an employer_id and only employer/search hands one out. Glassdoor serves different amounts of each surface to a signed-out visitor, so what is published here is what live calls actually returned rather than what the schema promises. Measured on 2026-09-24 against three employers - Google (9079), Stripe (671932) and Apple (1651) - with twelve runs per single-page action and six per harvest.
| Action | Result on 2026-09-24 | What the live calls returned |
|---|---|---|
| employer/search | 12/12 | Twelve distinct company names returned 37 rows in total, every one carrying employer_id and name. "Google" returned 1 row (9079), "Nvidia" returned 9. |
| employer/detail | 12/12 | Every advertised field arrived on all 12 calls: website, headquarters, size, industry, sector, description, review_count, salary_count, overall_rating, the nine sub-ratings, ceo, the star distribution, industry_benchmark_ratings, revenue, company_type and year_founded. |
| employer/reviews | 12/12 | 36 reviews, all carrying review_id, date, headline, pros, cons, overall_rating, employment_status and is_current_job. job_title was present on 32 of 36 - some reviewers do not give one. This is one page per sort order; see the FAQ below. |
| employer/reviews-harvest | 6/6 | 65 unique reviews across six runs, 9 to 12 per employer, against 3 from a single employer/reviews call. Slower than the other actions: 8s to 45s per call. |
| employer/interviews | 12/12 | 60 reports across four pages per employer, zero overlap between pages. interview_id, date, job_title, difficulty, experience, outcome and process_description on all 60. source on 24 of 60 and questions on 5 of 60 - both are optional for the person filing the report. |
| employer/salaries | 12/12 | 120 job titles across four pages per employer. job_title, job_title_id, salary_count, currency, most_recent, median_base_pay, median_total_pay and the full P10-P90 base_pay and total_pay bands on all 120 rows. |
| employer/jobs | 8/12, plus 4 honest empties | 10 rows each for Google and Apple with title, location, salary_min, salary_max, company_rating and job_url. Stripe returned zero rows with total_jobs_count 0 - Glassdoor's own US board has no Stripe listings, which is an answer rather than an error. |
employer_id is a plain integer with no prefix and no fixed width: 4 digits for long-established profiles (Google 9079, Apple 1651), 6 or 7 for newer ones (Stripe 671932). The same number appears twice more in a response, in the logo_url path (media.glassdoor.com/sqlm/9079/...) and as company_id on every job row.
Real request and response JSON
Captured from the indexed primary action, employer/search, on .
{
"method": "POST",
"url": "https://api.reefapi.com/glassdoor/v1/employer/search",
"headers": {
"x-api-key": "$REEF_KEY",
"content-type": "application/json"
},
"body": {
"query": "Google"
}
}{
"ok": true,
"meta": {
"api": "glassdoor",
"endpoint": "employer/search",
"mode": "live",
"latency_ms": 663.9,
"record_count": 1,
"bytes": 0,
"cache_hit": false,
"count": 1,
"charged_credits": 1,
"version": "1.2.0"
},
"data": {
"results": [
{
"employer_id": 9079,
"name": "Google",
"category": "company",
"logo_url": "https://media.glassdoor.com/sqlm/9079/google-squarelogo-1441130773284.png"
}
]
}
}What the Glassdoor API does
| Action | Description | Concrete use case | Key params |
|---|---|---|---|
| employer/search | Resolve a company name to its Glassdoor employer_id + basic profile. Start here — every other action needs the employer_id. | Recruiting teams call employer/search to resolve a company name to its Glassdoor employer_id + basic profile. | query |
| employer/detail | Full employer profile: firmographics, description and mission, the headline rating plus every sub-rating, the star breakdown, and how the company scores against its industry. | Labor-market analysts call employer/detail to get full employer profile. | employer_id |
| employer/reviews | The employer's public reviews (rating, pros/cons, role), plus the company-wide aggregate ratings and the full star distribution. Glassdoor shows signed-out visitors one page of reviews per sort order — for more of them call `employer/reviews-harvest`, which collects every sort order. | Job boards call employer/reviews to get the employer's public reviews (rating, pros/cons, role), plus the company-wide aggregate rati…. | employer_id |
| employer/reviews-harvest | Every review Glassdoor shows without signing in: the most recent, most helpful, highest-rated and lowest-rated reviews, de-duplicated into one list with the aggregate ratings and star distribution. | Sales intelligence teams call employer/reviews-harvest to get every review Glassdoor shows without signing in. | employer_id, max_pages |
| employer/interviews | One page of interview reports — difficulty, outcome, and the candidate's write-up of the process. `source` (how the candidate was sourced) and `questions` (structured questions the candidate attached) are filled in only when the reporter supplied them: measured across 60 reports from three employers, `source` arrived on 24 and `questions` on 5. The process itself is always described in `process_description`. | Recruiting teams call employer/interviews to get one page of interview reports. | employer_id, page, cursor |
| employer/interviews-harvest | Fetch Glassdoor interview reports across multiple pages. | Labor-market analysts call employer/interviews-harvest to fetch Glassdoor interview reports across multiple pages.. | employer_id, max_pages |
| employer/jobs | Employer job listings (one page; cursor pagination). | Job boards call employer/jobs to get employer job listings (one page; cursor pagination).. | employer_id, page, cursor, page_size, page_cursor |
| employer/jobs-harvest | Fetch all available Glassdoor job listings across multiple pages. | Sales intelligence teams call employer/jobs-harvest to fetch all available Glassdoor job listings across multiple pages.. | employer_id, page_size, max_pages |
| employer/salaries | Glassdoor salary estimates for this employer, broken down by job title. Each title returns its pay distribution — base pay and total pay percentiles (P10/P25/P50/P75/P90) with the medians. Titles are ordered by number of reported salaries (most-reported first). | Recruiting teams call employer/salaries to get glassdoor salary estimates for this employer, broken down by job title. | employer_id, page, cursor, pay_period |
| employer/salaries-harvest | Fetch salary estimates for many job titles at this employer across multiple pages — every title with its pay distribution. | Labor-market analysts call employer/salaries-harvest to fetch salary estimates for many job titles at this employer across multiple pages. | employer_id, pay_period, max_pages |
Call employer/search from your stack
curl -X POST https://api.reefapi.com/glassdoor/v1/employer/search \
-H "x-api-key: $REEF_KEY" \
-H "content-type: application/json" \
-d '{"query":"Google"}'import requests
r = requests.post(
"https://api.reefapi.com/glassdoor/v1/employer/search",
headers={"x-api-key": REEF_KEY},
json={
"query": "Google"
},
)
print(r.json()["data"])const res = await fetch("https://api.reefapi.com/glassdoor/v1/employer/search", {
method: "POST",
headers: {
"x-api-key": process.env.REEF_KEY,
"content-type": "application/json",
},
body: JSON.stringify({
"query": "Google"
}),
});
const { ok, data, meta, error } = await res.json();Ask your MCP-connected assistant: call reefapi.glassdoor.employer/search with {"query":"Google"}.Who uses this API and why
- Employer-branding teams call employer/detail to track their overall rating, every sub-rating and how they score against the industry benchmark.
- Recruiting tools use employer/salaries and employer/interviews to prep candidates with real pay bands and a real account of the process.
- Labor-market researchers use employer/detail across a company list to benchmark employer reputation, headcount and revenue in one call.
Questions developers ask before integrating
Why does employer/reviews return so few reviews for a company with tens of thousands?
Because that is all Glassdoor shows without an account. Review page 2 redirects to a sign-in wall - we measured it on an ordinary desktop Chrome as well as through the API, and on all eight Glassdoor country domains, so it is the site's rule rather than a limit of this API. Each sort order does return a different first page, so employer/reviews-harvest collects the most recent, most helpful, highest-rated and lowest-rated reviews and de-duplicates them: that took 3 reviews up to 9-12 per employer across six measured runs. The aggregate numbers are not limited this way - aggregate_ratings, rating_distribution and all_reviews_count describe the whole review base, and all_reviews_count was 71,197 for Google.
Is there a page or page_size parameter on reviews?
No, and that is deliberate. Glassdoor's public reviews page renders a fixed number of reviews and ignores any size hint, and page 2 is behind sign-in, so a page_size parameter here would have been a control that quietly did nothing. It was removed rather than left in the schema. Passing page=2 returns a typed NOT_AVAILABLE that explains the sign-in wall instead of failing silently. Interviews and salaries do paginate - pass page there and you get genuinely different rows, with zero overlap measured across pages 1 to 4.
Which actions are answering today?
All ten. Between August and 2026-09-24, employer/detail, employer/reviews, employer/interviews and employer/salaries returned TARGET_BLOCKED because they read an internal Glassdoor endpoint that the site itself stopped calling. They were rebuilt on the public pages on 2026-09-24 and now measure 12/12. If you cached the old behaviour or coded around those errors, you can drop the workaround.
Can I filter salaries to one job title?
Not through this action. Glassdoor's salaries page accepts a job-title query parameter and ignores it - we sent ?search=Software%20Engineer and got back the byte-identical unfiltered page - so the job_title parameter was removed rather than shipped as a no-op. Filter client-side on the job_title field, or page through: titles come back most-reported-first, so the roles you want are usually on the first page or two. pay_period is real and does work - switching to HOURLY moved Google's Software Engineer median from 184,722.83 to 87.97.
Which salary components come back?
base_pay and total_pay, each as a P10/P25/P50/P75/P90 band plus a median, with median_base_pay and median_total_pay as the headline numbers. The separate cash-bonus, stock, profit-sharing, sales-commission and tips bands are no longer in Glassdoor's payload on any row we saw across three employers and three pages each, so they were removed from the schema. median_additional_pay follows the same rule and comes back null.
employer/search returned results for a company that does not exist. Why?
It is a fuzzy name matcher and it does not return an empty list. The query "zzqqxx not a real company 8888" came back ok:true with 10 rows, led by Dunton Commercial Real Estate Company and Real Estate Service Solutions Company, because it matched the word "company". Compare results[0].name against what you asked for before feeding its employer_id into another call. Every row we saw carried category "company".
employer/jobs returned zero jobs. Is that a block?
Check total_jobs_count first. Stripe (671932) returned ok:true, zero rows and total_jobs_count 0 on four separate calls, and Glassdoor's own US board agrees - it carries no Stripe listings. A block arrives as an explicit error code, never as a quiet empty list. Note too that this action reads the US board, so it is not the way to size a non-US company's hiring.
What currency and pay period do job salaries use?
Across 15 job rows from two employers, salary_currency was "USD" and salary_period was "ANNUAL" on every single row. salary_min and salary_max are plain integers with no separators and no decimals, for example 224000 and 311000. Both were populated on all 15 rows, but treat them as a band rather than a posted figure.
Is job_id stable between calls?
No, and this bites anyone using it as a primary key. Two identical calls seconds apart returned the same three jobs as 5-yul1-0-1k1048kv622rs000-c6f51a806240dca6 and 5-yul1-0-1k1048lungmsj800-c6f51a806240dca6: same leading segment, same trailing hash, different middle segment. Only the last dash-separated hash identifies the job. Dedupe on that segment, or on the jobListingId query parameter inside job_url.
How fast are these calls?
Median latency measured on 2026-09-24: employer/search about 0.9s, employer/jobs about 1.0s, employer/interviews about 1.5s, employer/salaries about 1.6s, employer/reviews about 1.7s and employer/detail about 2.6s. Harvests fetch several pages, so they are slower - interviews-harvest and salaries-harvest came in under 2s, reviews-harvest ran 8s to 45s. Give harvest calls a generous deadline_ms; they return what they collected rather than failing if they run long.
What is the Glassdoor API?
Glassdoor API is a ReefAPI endpoint group for company reviews, ratings and salary insights. It returns live JSON through POST requests under /glassdoor/v1.
Is the Glassdoor API free to try?
Yes. ReefAPI starts with 1,000 free credits, no card required. Glassdoor calls use the same shared credit balance as every other ReefAPI engine.
Do I need a Glassdoor login or account?
No login to Glassdoor is needed for the API response. You call ReefAPI with your x-api-key header, and the playground can run live examples before you create a production key.
How fresh is the Glassdoor data?
The page example is captured from a live employer/search call, and production requests fetch live data through ReefAPI rather than a static sample.