# Workday Jobs Scraper — Any myworkdayjobs.com Career Site (`arcaedion/workday-jobs-scraper`) Actor

Scrape every open job from any Workday career site (company.wdN.myworkdayjobs.com). Paste career site URLs and get clean, normalized jobs with location, remote flag, employment type, posting date and full description, plus new-jobs-only monitoring.

- **URL**: https://apify.com/arcaedion/workday-jobs-scraper.md
- **Developed by:** [Mathews Motta](https://apify.com/arcaedion) (community)
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.50 / 1,000 job returneds

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

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

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
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.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## 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.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## Workday Jobs Scraper — scrape any myworkdayjobs.com career site

Workday jobs scraper for any company career site hosted on `*.myworkdayjobs.com`. Paste career site URLs and get every open job as clean, normalized JSON - no browser, no proxy, no login. Workday powers the career sites of thousands of large employers, and this actor reads the same public job feed the career site itself uses.

### Features

- **Any Workday career site** - URLs like `https://nvidia.wd5.myworkdayjobs.com/NVIDIAExternalCareerSite`. Locale segments (`/en-US/`) and links to a single job posting are accepted too.
- **Full job data** - title, locations, remote flag, employment type, posting date, full description and the public apply link.
- **Server-side keyword search** - keywords are sent to Workday's own search, so a 2,000-job career site is not paged in full when you only need "data engineer".
- **Filters** - keywords, exclude keywords, locations, remote only, posted within N days.
- **New-jobs monitoring** - schedule it and receive only postings you have not seen before.

### Use cases

Recruiting and sourcing pipelines, competitor hiring tracking, labor-market research, job boards that need fresh enterprise listings, and alerts when a target employer posts a role.

### Pricing

**$1.50 per 1,000 jobs, pay only for jobs returned.** There is no charge for the run itself, for failed or unresolved entries, for duplicates, or for jobs removed by your filters. Set a maximum cost on the run and it stops cleanly when the limit is reached.

### Input

```json
{
    "companies": ["https://nvidia.wd5.myworkdayjobs.com/NVIDIAExternalCareerSite","https://salesforce.wd12.myworkdayjobs.com/External_Career_Site"],
    "keywords": ["data engineer"],
    "maxJobsPerCompany": 20
}
```

Each entry in **companies** is a Workday career site URL. Entries that belong to another ATS are reported as errors for that entry only, and the rest of the run continues. For other applicant tracking systems, or to find a board from a website or company name, use the **Multi-ATS Jobs Scraper** (see below).

### Output

Each job is one dataset item with a stable `id`. Main fields: title, company, locations, remote, employmentType, postedAt, url, applyUrl, descriptionText (and descriptionHtml on request), plus stable `id` and `scrapedAt`. Workday does not publish salary ranges or departments in its public feed, so `department` and `salaryMin/salaryMax` are usually `null`. `postedAt` comes from the posting's start date when descriptions are included, otherwise it is derived from Workday's relative "Posted N days ago" text.

Example item (description shortened):

```json
{
    "id": "workday:salesforce:JR364968",
    "source": "workday",
    "title": "Software Engineering SMTS",
    "company": "Salesforce",
    "companySlug": "salesforce/wd12/External_Career_Site",
    "url": "https://salesforce.wd12.myworkdayjobs.com/External_Career_Site/job/California---San-Francisco/Software-Engineering-SMTS_JR364968-1",
    "applyUrl": "https://salesforce.wd12.myworkdayjobs.com/External_Career_Site/job/California---San-Francisco/Software-Engineering-SMTS_JR364968-1/apply",
    "locations": [
        "California - San Francisco",
        "Washington - Bellevue"
    ],
    "remote": false,
    "employmentType": "Full time",
    "postedAt": "2026-10-22T00:00:00.000Z",
    "descriptionText": "To get the best candidate experience, please consider applying for a maximum of 3 roles within 12 months...",
    "scrapedAt": "2026-10-23T00:27:08.458Z"
}
```

A `SUMMARY` record in the key-value store lists, per input entry, the board that was resolved, jobs found, jobs output and any error.

### Monitor for new jobs

Turn on **Only new jobs** and give the run a **Monitor name**. The first run outputs all matching jobs and remembers them; every later run outputs only postings that appeared since. Schedule it daily or hourly and send the results to Slack, email, a webhook or a spreadsheet through Apify integrations. Use a different monitor name per company list or filter set.

### FAQ

**How do I find the Workday career site URL?**
Open the company's careers page, click through to the job search, and copy the address from the browser. It looks like `https://<company>.wd<N>.myworkdayjobs.com/<SiteName>`. A company name alone is not enough, because Workday site names cannot be guessed.

**Why is a run with descriptions slower?**
Workday only returns descriptions through one extra request per job. For very large career sites switch **Include job description** off, or set **Max jobs per company**.

**Does it need proxies or a login?**
No. It uses the public job feed of the career site over plain HTTP.

**Is scraping Workday career sites legal?**
The actor reads only publicly available job postings, the same data any visitor sees, and keeps the link to the original posting in every record. You are responsible for using the data in line with applicable laws and the terms of the sites involved.

### Related actors

- **[Multi-ATS Jobs Scraper](https://apify.com/arcaedion/ats-jobs-scraper)** - Greenhouse, Lever, Ashby, SmartRecruiters, Workable, Recruitee, Personio and Workday in one actor, with automatic detection from a website or company name.
- **[Company Hiring Signals](https://apify.com/arcaedion/company-hiring-signals)** - turn a list of companies into hiring activity signals.

# Actor input Schema

## `companies` (type: `array`):

One <b>myworkdayjobs.com</b> career site URL per company, e.g. <code>https://nvidia.wd5.myworkdayjobs.com/NVIDIAExternalCareerSite</code>. Copy it from the browser address bar on the company's Workday job search page - locale segments such as <code>/en-US/</code> and links to a single job are fine, the career site is extracted automatically. Workday site names cannot be guessed from a company name, so a URL is required. Entries that fail are reported in the SUMMARY record and never stop the run or cost anything.

## `keywords` (type: `array`):

Only keep jobs whose <b>title or description</b> contains at least one of these words or phrases (case-insensitive). Leave empty to keep everything. Example: <code>data engineer</code>, <code>python</code>. For Workday the keywords are also sent to Workday's own search, so large career sites are not paged in full.

## `excludeKeywords` (type: `array`):

Drop jobs whose <b>title</b> (or department) contains any of these words (case-insensitive). Example: <code>intern</code>, <code>sales</code>.

## `locations` (type: `array`):

Only keep jobs located in at least one of these places. Matched as a case-insensitive substring of the job's location text, so use whatever the company uses: <code>Berlin</code>, <code>United States</code>, <code>London</code>, <code>Remote</code>.

## `remoteOnly` (type: `boolean`):

Keep only jobs that are explicitly remote - flagged by the ATS or with 'remote' in the title / location. Jobs where remote status is unknown are dropped.

## `postedWithinDays` (type: `integer`):

Only keep jobs first published in the last N days. 0 disables the filter. Jobs without a publish date are dropped when this is set. Note: Workday only exposes a relative date for list results ('Posted 30+ Days Ago'), which is approximated.

## `departments` (type: `array`):

Only keep jobs whose department or team contains one of these words (case-insensitive substring), e.g. <code>Engineering</code>, <code>Product</code>. Workday does not expose departments, so its jobs never match this filter.

## `onlyNewJobs` (type: `boolean`):

Output only jobs not seen in a previous run with the same <b>Monitor name</b>. Schedule the Actor daily to get just the fresh postings. <b>The first run of a monitor outputs all matching jobs</b> (and remembers them as the baseline); every later run outputs only newly appeared ones. Already-seen and filtered-out jobs are never output or charged.

## `monitorName` (type: `string`):

Identifies the saved list of already-seen jobs for 'Only new jobs'. Use different names for different company lists or filters (e.g. <code>fintech-engineering</code>) so they track new jobs independently. State is stored per name in a named key-value store under your account.

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

Add the plain-text job description (<code>descriptionText</code>). Workday needs one extra request per job for this, so large career sites run much faster when it is off (descriptions are still fetched internally if a keyword filter needs them).

## `includeDescriptionHtml` (type: `boolean`):

Also add the original HTML of the description (<code>descriptionHtml</code>). Increases dataset size.

## `maxJobsPerCompany` (type: `integer`):

Cap on jobs output per company, applied after filters. 0 means unlimited. Useful for very large employers (thousands of openings) and for quick test runs.

## Actor input object example

```json
{
  "companies": [
    "https://nvidia.wd5.myworkdayjobs.com/NVIDIAExternalCareerSite",
    "https://adobe.wd5.myworkdayjobs.com/en-US/external_experienced"
  ],
  "keywords": [
    "data engineer",
    "machine learning"
  ],
  "excludeKeywords": [
    "intern",
    "sales"
  ],
  "locations": [
    "Berlin",
    "London"
  ],
  "remoteOnly": false,
  "postedWithinDays": 7,
  "departments": [
    "Engineering"
  ],
  "onlyNewJobs": false,
  "monitorName": "default",
  "includeDescription": true,
  "includeDescriptionHtml": false,
  "maxJobsPerCompany": 50
}
```

# Actor output Schema

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

One normalized record per job posting.

## `summary` (type: `string`):

Per-company status, counts, failures and charged items for this run.

# 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 = {
    "companies": [
        "https://nvidia.wd5.myworkdayjobs.com/NVIDIAExternalCareerSite",
        "https://salesforce.wd12.myworkdayjobs.com/External_Career_Site",
        "https://workday.wd5.myworkdayjobs.com/Workday"
    ],
    "includeDescription": true,
    "maxJobsPerCompany": 20
};

// Run the Actor and wait for it to finish
const run = await client.actor("arcaedion/workday-jobs-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 = {
    "companies": [
        "https://nvidia.wd5.myworkdayjobs.com/NVIDIAExternalCareerSite",
        "https://salesforce.wd12.myworkdayjobs.com/External_Career_Site",
        "https://workday.wd5.myworkdayjobs.com/Workday",
    ],
    "includeDescription": True,
    "maxJobsPerCompany": 20,
}

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

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

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

```

## CLI example

```bash
echo '{
  "companies": [
    "https://nvidia.wd5.myworkdayjobs.com/NVIDIAExternalCareerSite",
    "https://salesforce.wd12.myworkdayjobs.com/External_Career_Site",
    "https://workday.wd5.myworkdayjobs.com/Workday"
  ],
  "includeDescription": true,
  "maxJobsPerCompany": 20
}' |
apify call arcaedion/workday-jobs-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,arcaedion/workday-jobs-scraper"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/4d1CU1skMNleqOKaD/builds/C2rKBxvlJYjtXlRls/openapi.json
