# EdJoin Jobs Scraper: Educator & School District Listings (`getascraper/edjoin-scraper`) Actor

Extract EdJoin teaching, administrative, and classified K-12 school job listings. Collect contact emails, salary ranges, deadlines, and requirements. Direct fast JSON API crawling with JSON-LD detail mapping. Best value at an affordable price.

- **URL**: https://apify.com/getascraper/edjoin-scraper.md
- **Developed by:** [GetAScraper](https://apify.com/getascraper) (community)
- **Categories:** Jobs, Lead generation, Automation
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.12 / 1,000 jobs

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

Learn more: https://docs.apify.com/platform/actors/running/actors-in-store#pay-per-event

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.
Actors are written with capital "A".

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## 🎓 EdJoin scraper: K-12 teaching, certificated and classified job listings

Get instant, structured access to K-12 education jobs across US school districts. Extract direct HR contact emails, salary ranges, deadlines, locations, and requirements in bulk with zero visual DOM fragility.

### 🔍 What does EdJoin Scraper do?

The **EdJoin Scraper** is a fast web crawling tool that extracts complete education vacancy listings from **EdJoin** (edjoin.org), the largest job board for public and private school districts in the United States.

It pulls data from two main sources:

1. **Listing Search API**: Queries EdJoin's backend JSON search index directly to discover postings based on keywords and locations. This allows high-concurrency, fast walks of thousands of records with zero web browser overhead.
2. **Detail Page JSON-LD Parsing**: Loads the detail page of each discovered vacancy to extract structured Schema.org `JobPosting` JSON-LD blocks containing direct school contact emails, full credential requirements, and required skills.

With Apify, you can run this scraper via a simple REST API, schedule it to run daily or weekly to monitor new postings, and automatically integrate the results with Google Sheets, Airtable, Make, or webhooks.

### 🎯 Why use EdJoin Scraper?

- **Find High-Intent HR & Recruiting Leads**: For staffing agencies, B2B marketers, and recruiting firms looking to discover direct contact emails of hiring managers and school district coordinators.
- **Keep Your Education Career Board Updated**: Keep your own education career board up-to-date with complete vacancy metadata, direct links, salary structures, and expiration dates.
- **Benchmark Teacher Salaries & Benefits**: Analyze teacher salaries, work schedules, required certifications, and posting volumes across districts, counties, and states.
- **Set Up Daily Automated Alerts**: Schedule the scraper to run daily to detect fresh vacancies matching your criteria (e.g. "Special Education Teacher" in "Los Angeles") and send instant notifications to your teams.

### 🚀 How to use EdJoin Scraper

1. **Set Up**: Open the EdJoin Scraper page in the Apify Console.
2. **Configure Input**: Set the search `keyword` (e.g., *Special Education*) and `location` (e.g., *California*).
3. **Limit Output**: Set `maxItems` to restrict the number of results collected to control costs.
4. **Choose Mode**: Enable `includeDescription` to visit detailed pages for direct emails and qualifications, or disable it for a super-fast, cheap listing-only query.
5. **Run**: Click the **Start** button. Once completed, download your data in JSON, CSV, Excel, or HTML format in the Output tab.

***

### 📋 Input Parameters

The scraper accepts these input configuration settings:

| Field | Type | Description | Default |
| --- | --- | --- | --- |
| `startUrls` | Array | Optional pre-filtered EdJoin search URLs to scrape. | `[]` |
| `keyword` | String | Search keyword for role, specialty, or district (e.g. "Teacher", "Secretary"). | `"Teacher"` |
| `location` | String | Geographic area (e.g. "California", "San Diego", "90210"). | `"California"` |
| `maxItems` | Integer | Maximum number of job records to collect. | `100` |
| `includeDescription` | Boolean | Whether to fetch detailed pages for HR emails, requirements, and logos. | `true` |
| `dateWithinDays` | Integer | Only include postings created within the last N days (0 = any time). | `0` |
| `maxConcurrency` | Integer | Maximum parallel page requests. | `8` |
| `proxyConfiguration` | Object | Proxy routing. Standard open WAF allows running without proxies. | `{"useApifyProxy": false}` |

***

### 📤 Output Structure

The scraper outputs fully normalized flat job rows with empty fields omitted. Here is a sample JSON representation:

```json
{
  "posting_id": 2234074,
  "title": "Secretary II (School) at Cajon Park - Pos#30024578",
  "district_name": "Santee School District",
  "city": "Santee",
  "county_name": "San Diego",
  "state_name": "California",
  "postal_code": "92071-2674",
  "address": "9625 Cuyamaca St.",
  "job_type": "Clerical / Secretarial Staff / Office Tech.",
  "employment_type": "FULL_TIME",
  "salary_info": "Salary Classification: 27",
  "pay_range_from": "Salary Classification: 27/ Step A",
  "pay_range_to": "Salary Classification: Step E",
  "pay_range_unit": "Monthly",
  "single_rate": null,
  "single_rate_unit": null,
  "contact_email": "brandi.medrano@santeesd.net",
  "date_posted": "2026-06-06T07:00:00.000Z",
  "deadline": "2026-06-12T23:00:00.000Z",
  "work_hours": "203 work days / 8.0 hrs. / 7:00 a.m. - 3:30 p.m.",
  "requirements": "MINIMUM QUALIFICATIONS / CERTIFICATIONS / AND APPLICATION PROCEDURE: See job description for a complete list of qualifications and requirements at www.santeesd.net; under the Human Resources department. Applications, transcripts, certification(s), and / or documentation MUST be submitted for each position...",
  "required_skills": "First Aid, CPR and AED Certificate (All three trainings required) Online training certificates accepted. Typing Certificate 50 nwpm (net words per minute)",
  "logo": "https://edjoinprodstoragewest.blob.core.windows.net/customerlogos/logo133892042317467324.png",
  "url": "https://www.edjoin.org/Home/JobPosting/2234074",
  "scraped_at": "2026-06-07T05:22:15.341Z"
}
```

***

### 📊 Output Fields Explanation

| Field Name | Type | Description |
| --- | --- | --- |
| `posting_id` | Number | Unique identifier for the vacancy posting. |
| `title` | String | Job position title. |
| `district_name` | String | School district or hiring agency name. |
| `city` | String | Primary city. |
| `county_name` | String | County name where the position resides. |
| `state_name` | String | State name (e.g. California). |
| `postal_code` | String | Location ZIP or postal code. |
| `address` | String | Physical street address of the district. |
| `job_type` | String | Broad classification group. |
| `employment_type` | String | Full Time, Part Time, or other employment status. |
| `salary_info` | String | Raw salary text. |
| `pay_range_from` | String | Stated lower bound of the pay schedule. |
| `pay_range_to` | String | Stated upper bound of the pay schedule. |
| `pay_range_unit` | String | Unit rate of the pay range (Monthly, Hourly, Annually). |
| `single_rate` | String | Stated flat pay rate if no range is given. |
| `contact_email` | String | Direct HR contact email address. |
| `date_posted` | String | ISO formatted publication date. |
| `deadline` | String | ISO formatted application closing date. |
| `work_hours` | String | Work shift, day, or calendar schedules. |
| `requirements` | String | Detailed qualifications description. |
| `required_skills` | String | Explicit certificates or typing requirements. |
| `logo` | String | Hiring organization logo URL. |
| `url` | String | Link to the original posting. |
| `scraped_at` | String | Scraping execution timestamp. |

***

### 💰 Cost Estimation & Pricing

Because this Actor uses an API-driven listing crawl and lightweight Cheerio detail fetch, it does not require running dynamic browser instances (Playwright/Puppeteer), which reduces compute overhead. It can be run successfully on standard datacenter IPs.

- **Standard platform rate**: **$1.99 per 1,000 results** (excludes micro platform execution fees).
- Running a 5,000 vacancy crawl will cost approximately $9.95 in bandwidth and compute units combined.

***

### ⭐ Enjoying EdJoin Scraper?

<table width="100%">
<tr>
<td style="padding:20px 24px 14px;background:#EAF1FB;border:1px solid #EAF1FB;border-left:5px solid #1D4E89;border-radius:10px 10px 0 0">
<span style="font-size:20px;letter-spacing:4px">⭐ ⭐ ⭐ ⭐ ⭐</span><br>
<span style="font-size:17px;font-weight:800;color:#1C1917">One run just surfaced direct HR contact emails across hundreds of school district postings.</span><br>
<span style="font-size:14px;color:#57534E">A 5-star rating takes 10 seconds and helps other staffing agencies and recruiters find this actor. Your feedback also tells us what to build next.</span>
</td>
</tr>
<tr>
<td style="padding:0;background:#1D4E89;border:1px solid #EAF1FB;border-top:none;border-radius:0 0 10px 10px;text-align:center">
<a href="https://apify.com/getascraper/edjoin-scraper/reviews" style="display:block;padding:13px 16px;color:#FFFFFF;text-decoration:none;font-weight:800;font-size:15px;letter-spacing:0.3px">★&nbsp;&nbsp;Rate this Actor on Apify</a>
</td>
</tr>
</table>

***

### ❓ FAQ, Disclaimers, and Support

- **Is scraping EdJoin legal?**
  Yes. This scraper extracts publicly available recruitment listings that districts intend to share with the public. It does not access private applicant data or require logging in. Ensure you comply with local regulations and respect server load limits by setting standard concurrency.
- **Can I run this on a schedule?**
  Yes. In the Apify Console, create a Schedule to trigger the actor daily, weekly, or monthly.
- **How can I submit suggestions or bugs?**
  Open an issue in the **Issues** tab on this Actor's page, or contact us through the Apify Console.

### 🔗 Other actors

- [Goodmoves Jobs Scraper](https://apify.com/getascraper/goodmoves-jobs-scraper) ↗ - extracts Scottish charity sector job listings with OSCR charity numbers.
- [HigherEdJobs Scraper: Academic & University Listings](https://apify.com/getascraper/higheredjobs-com-scraper) ↗ - extracts university and academic job postings across the US.
- [WTTJ Jobs Scraper: Raw JSON or RAG-Ready Chunks](https://apify.com/getascraper/welcome-to-the-jungle-jobs-scraper) ↗ - extracts job listings from Welcome to the Jungle.
- [CWJobs Scraper: UK Tech Jobs, Salaries & Geo](https://apify.com/getascraper/cwjobs-scraper) ↗ - extracts UK tech job listings with salary and location data.
- [Job Bank Canada Scraper](https://apify.com/getascraper/jobbank-scraper) ↗ - extracts B2B job listings and employer contacts from Canada's national job directory.

# Actor input Schema

## `startUrls` (type: `array`):

Optional EdJoin search URLs to scrape. If provided, it overrides custom search filters.

## `keyword` (type: `string`):

Search for specific jobs by role, specialty, or district (e.g., 'Special Education', 'Math Teacher').

## `location` (type: `string`):

Filter by city, county, state, or ZIP code (e.g., 'California', 'San Diego').

## `includeDescription` (type: `boolean`):

If enabled, visits each job's detailed page to extract full requirements and descriptions. Slower but richer data.

## `dateWithinDays` (type: `integer`):

Only include jobs posted within the last N days (0 = any time).

## `maxItems` (type: `integer`):

Maximum number of job postings to scrape in total.

## `maxConcurrency` (type: `integer`):

Maximum number of requests handled in parallel.

## `maxRequestRetries` (type: `integer`):

Number of times a request will be retried if it fails.

## `proxyConfiguration` (type: `object`):

Proxy settings for crawling. Enabling proxy is recommended for larger crawls to prevent connection throttling.

## Actor input object example

```json
{
  "startUrls": [],
  "keyword": "Teacher",
  "location": "California",
  "includeDescription": true,
  "dateWithinDays": 0,
  "maxItems": 5,
  "maxConcurrency": 8,
  "maxRequestRetries": 3,
  "proxyConfiguration": {
    "useApifyProxy": true
  }
}
```

# Actor output Schema

## `results` (type: `string`):

No description

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "startUrls": [],
    "keyword": "Teacher",
    "location": "California",
    "dateWithinDays": 0,
    "maxItems": 5,
    "proxyConfiguration": {
        "useApifyProxy": true
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("getascraper/edjoin-scraper").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "startUrls": [],
    "keyword": "Teacher",
    "location": "California",
    "dateWithinDays": 0,
    "maxItems": 5,
    "proxyConfiguration": { "useApifyProxy": True },
}

# Run the Actor and wait for it to finish
run = client.actor("getascraper/edjoin-scraper").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print("💾 Check your data here: https://console.apify.com/storage/datasets/" + run["defaultDatasetId"])
for item in client.dataset(run["defaultDatasetId"]).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "startUrls": [],
  "keyword": "Teacher",
  "location": "California",
  "dateWithinDays": 0,
  "maxItems": 5,
  "proxyConfiguration": {
    "useApifyProxy": true
  }
}' |
apify call getascraper/edjoin-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "command": "npx",
            "args": [
                "mcp-remote",
                "https://mcp.apify.com/?tools=getascraper/edjoin-scraper",
                "--header",
                "Authorization: Bearer <YOUR_API_TOKEN>"
            ]
        }
    }
}

```

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/PV0zkoqhselkr6vUF/builds/ch30mTOhMvK9MbIk5/openapi.json
