# Remote Jobs Aggregator – Europe-friendly remote jobs (`benelux-signals/remote-jobs-aggregator`) Actor

Remote jobs from Jobicy, Remote OK, We Work Remotely, Working Nomads and Arbeitnow in one clean JSON feed: region filter (Europe, worldwide…), salary, tags, de-duplicated. Only-new mode.

- **URL**: https://apify.com/benelux-signals/remote-jobs-aggregator.md
- **Developed by:** [Benelux Signals](https://apify.com/benelux-signals) (community)
- **Categories:** Jobs, Automation, Developer tools
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.00 / 1,000 job postings

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/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

## Remote Jobs Aggregator – Europe-friendly remote jobs

**Get remote job postings from five public remote-job boards in one clean, de-duplicated JSON feed, from $0.001 per job.** The Actor reads **Jobicy, Remote OK, We Work Remotely, Working Nomads and Arbeitnow**, merges the same job posted on several boards into one record, and tells you **where you can work from**: worldwide, Europe, North America, LATAM, APAC, Africa or the Middle East. Filter by keyword, region, employment type, salary and posting date, and turn on *only new jobs* for a daily feed.

### Who is this remote jobs scraper for?

- **Job boards and newsletters** that publish curated remote jobs for Europe or a niche (Python, design, marketing) and want one feed instead of five.
- **Recruiters and sourcing teams** looking for companies that hire remotely in Europe, with salary data where the board has it.
- **Job seekers and career coaches** who want a daily alert for "remote data engineer, Europe-friendly, with salary" in Slack, Sheets or e-mail.
- **Analysts** tracking remote-hiring trends: which companies, roles, salaries and regions.

### What does it do?

1. Loads the latest postings from the boards you select (public RSS feeds and public JSON APIs, no login).
2. Cleans the data: HTML to plain text, broken characters repaired, e-mail addresses and phone numbers removed from descriptions.
3. Classifies each job's location into regions (`regions`) and sets `europeFriendly` when you can work from Europe.
4. Merges duplicates (same company + title) across boards; the other boards are listed in `alsoListedOn`.
5. Applies your filters, sorts newest first and saves up to `maxResults` jobs.

Each job links back to the original posting on the source board (`jobUrl`, `applyUrl`) and carries an `attribution` line. Please keep that link when you republish jobs – the boards ask for it.

### Input example

```json
{
  "keywords": ["python", "data engineer"],
  "regions": ["europe"],
  "includeWorldwide": true,
  "employmentTypes": ["full-time"],
  "postedWithinDays": 14,
  "withSalaryOnly": false,
  "onlyNewJobs": false,
  "maxResults": 200
}
```

- `keywords` match whole words in title, category and tags (add `searchInDescription` for the full text). `excludeKeywords` drops jobs whose title or company contains a word, for example `senior`.
- `regions`: `worldwide`, `europe`, `north-america`, `latam`, `apac`, `africa`, `middle-east`. Worldwide jobs are included unless you turn off `includeWorldwide`; jobs without a usable location are skipped unless you turn on `includeUnspecifiedLocation`.
- `sources`: pick any of `jobicy`, `remoteok`, `weworkremotely`, `workingnomads`, `arbeitnow`.
- `onlyNewJobs` + `stateKey`: remember jobs between runs and save only new ones (kept for 120 days).

### Output example

```json
{
  "status": "ok",
  "jobId": "jobicy:157567",
  "source": "jobicy",
  "sourceName": "Jobicy",
  "title": "Regulatory Manager / Senior Regulatory Manager",
  "company": "Precision Medicine Group",
  "location": "Poland",
  "regions": ["europe"],
  "countries": [],
  "europeFriendly": true,
  "employmentType": "full-time",
  "seniority": "senior",
  "category": "Legal & Compliance",
  "tags": ["legal & compliance"],
  "salaryMin": 190200,
  "salaryMax": 285400,
  "salaryCurrency": "PLN",
  "salaryPeriod": "year",
  "salaryText": "190,200–285,400 PLN / year",
  "postedAt": "2026-10-28T13:21:44.000Z",
  "jobUrl": "https://jobicy.com/jobs/157567-regulatory-manager-senior-regulatory-manager",
  "applyUrl": "https://jobicy.com/jobs/157567-regulatory-manager-senior-regulatory-manager",
  "description": "Precision for Medicine is not your typical CRO. …",
  "alsoListedOn": [],
  "attribution": "Job via Jobicy (https://jobicy.com) – apply through the Jobicy job URL"
}
```

The dataset has three views: **Overview**, **Salaries** and **Europe-friendly**. A `RUN_SUMMARY` record in the key-value store shows how many jobs each board returned, how many were merged and why jobs were filtered out. If one board is down, you get a free `error` row for it and the other boards still deliver.

### How much does it cost?

Pay per event: **$0.005 per run start** plus **$0.0015 per job** on the free plan, $0.0013 on Bronze, $0.0012 on Silver and **$0.001 on Gold** and higher. 200 Europe-friendly jobs cost about $0.21–0.31. Error rows, the no-results row, merged duplicates, filtered-out jobs and jobs skipped by only-new mode are **free**. With only-new mode a daily feed usually costs a few cents per day.

### FAQ

**Is it legal?** The Actor only reads public job postings that the boards publish in public feeds and APIs for exactly this kind of reuse, at a low request rate (a few dozen requests per run). It follows their conditions: every job links back to the original posting and names the source. It does not output contact persons; e-mail addresses and phone numbers are removed from descriptions. You are responsible for how you republish the data.

**How often should I run it?** Once or a few times per day is plenty – the boards add a few hundred remote jobs per day. Please do not schedule it more than **once per hour**; Jobicy asks API users to poll at most hourly.

**Why does a board return fewer jobs than its website?** The public feeds contain the latest jobs (Remote OK ~100, Working Nomads ~40, We Work Remotely ~450, Jobicy ~1,000 from the last week, Arbeitnow remote jobs of the last weeks). This Actor is built for fresh jobs and daily feeds, not for an archive.

**How accurate is the region filter?** Regions come from the board's location text (countries, cities, time zones such as CET, "EMEA", "Anywhere"). "Remote" without a place counts as worldwide. Jobs that name only US or Canadian places are classed as North America.

**Can I get Greenhouse/Lever jobs or German on-site jobs too?** Yes, see the related actors below.

### Related actors by benelux-signals

Cover the rest of the European job market:

- [Career Site Jobs API](https://apify.com/benelux-signals/eu-career-site-jobs-api) – jobs straight from Greenhouse, Lever, Recruitee, Personio, Ashby and other company career sites.
- [Workday Jobs API](https://apify.com/benelux-signals/workday-jobs-api-europe) – jobs from any myworkdayjobs.com career site, with a European employer seed list.
- [Arbeitsagentur Jobs API](https://apify.com/benelux-signals/arbeitsagentur-jobs-api) – German job ads from the Bundesagentur für Arbeit Jobbörse.

More tools from the same maintainer:

- [EU Tender Radar](https://apify.com/benelux-signals/eu-tender-radar) – TED + TenderNed public tenders with keyword/CPV filters and only-new alerts.
- [Benelux Trade Fair Exhibitors](https://apify.com/benelux-signals/benelux-trade-fair-exhibitors) – exhibitor lists from Dutch and Belgian trade fairs (Horecava, METSTRADE, Batibouw…) for B2B lead lists.
- [Bulk PageSpeed & SEO Audit](https://apify.com/benelux-signals/bulk-pagespeed-seo-audit) – Core Web Vitals, Lighthouse scores and on-page SEO checks for many URLs or a sitemap.
- [EU & Dutch News Monitor](https://apify.com/benelux-signals/eu-news-rss-monitor) – keyword alerts across 80+ built-in Dutch, Belgian and EU news and official RSS feeds.
- [PDF & Image to Text OCR](https://apify.com/benelux-signals/pdf-image-to-text-ocr) – text and Markdown from PDFs and scans, ready for RAG and AI agents.
- [Technical SEO Site Crawler](https://apify.com/benelux-signals/technical-seo-site-crawler) – crawl a site for broken links, redirects, missing titles/meta, canonicals and noindex issues.

Questions or a source we should add? Open an issue on the Actor page.

# Actor input Schema

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

Keep jobs whose title, category or tags contain at least one of these words (whole-word, case-insensitive), e.g. python, react, designer, customer support. Empty = all remote jobs.

## `regions` (type: `array`):

Only jobs open to candidates in these regions. Leave empty for all. 'europe' also matches EMEA, CET/GMT time zones and European countries/cities.

## `includeWorldwide` (type: `boolean`):

With a region filter, also keep jobs that are open worldwide.

## `includeUnspecifiedLocation` (type: `boolean`):

Some boards (mostly Remote OK) leave the location empty. With a region filter these are dropped unless you enable this.

## `sources` (type: `array`):

Which boards to aggregate. Empty = all five.

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

Drop jobs whose title or company contains one of these words, e.g. senior, crypto, sales.

## `employmentTypes` (type: `array`):

Only these types. Empty = all (jobs without a stated type are kept only when this is empty).

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

Only jobs published in the last N days. 0 = no limit (boards themselves keep roughly the last 1–6 weeks).

## `withSalaryOnly` (type: `boolean`):

Keep only jobs that state a salary (mostly Jobicy and Remote OK).

## `searchInDescription` (type: `boolean`):

Also search the full description text. Finds more jobs, but also looser matches.

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

Plain-text description (contact e-mails and phone numbers removed). Turn off for smaller, faster output.

## `deduplicate` (type: `boolean`):

The same job (same company + title) on several boards becomes one record with 'alsoListedOn'.

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

Skip jobs this Actor already delivered in earlier runs with the same stateKey (free). Perfect for a daily schedule.

## `stateKey` (type: `string`):

Name of the 'already delivered' memory used by onlyNewJobs. Use one per saved task.

## `maxResults` (type: `integer`):

Maximum number of jobs to save (and pay for), newest first.

## Actor input object example

```json
{
  "keywords": [
    "python",
    "data engineer"
  ],
  "regions": [
    "europe"
  ],
  "includeWorldwide": true,
  "includeUnspecifiedLocation": false,
  "sources": [
    "jobicy",
    "remoteok",
    "weworkremotely",
    "workingnomads",
    "arbeitnow"
  ],
  "excludeKeywords": [],
  "employmentTypes": [],
  "postedWithinDays": 30,
  "withSalaryOnly": false,
  "searchInDescription": false,
  "includeDescription": true,
  "deduplicate": true,
  "onlyNewJobs": false,
  "stateKey": "default",
  "maxResults": 200
}
```

# Actor output Schema

## `overview` (type: `string`):

All jobs in the 'overview' table view.

## `runSummary` (type: `string`):

JSON summary (jobs per board, duplicates merged, filtered-out and already-seen counts) stored under RUN_SUMMARY.

# 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 = {
    "keywords": [
        "python",
        "data engineer"
    ],
    "regions": [
        "europe"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("benelux-signals/remote-jobs-aggregator").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 = {
    "keywords": [
        "python",
        "data engineer",
    ],
    "regions": ["europe"],
}

# Run the Actor and wait for it to finish
run = client.actor("benelux-signals/remote-jobs-aggregator").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 '{
  "keywords": [
    "python",
    "data engineer"
  ],
  "regions": [
    "europe"
  ]
}' |
apify call benelux-signals/remote-jobs-aggregator --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,benelux-signals/remote-jobs-aggregator"
        }
    }
}
```

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/10f9KXSOAc68zNmx3/builds/qUSIDrtvUUaRb6oWb/openapi.json
