Malt Fr Scraper avatar

Malt Fr Scraper

Pricing

from $2.80 / 1,000 results

Go to Apify Store
Malt Fr Scraper

Malt Fr Scraper

Scrape freelance profiles from the Malt directory (malt.fr, malt.de, malt.es): name, headline, skills, day rate, location, rating, missions and recommendations. Search by skill, role or city. Backed by Malt's internal JSON search API.

Pricing

from $2.80 / 1,000 results

Rating

0.0

(0)

Developer

Ahmed Jasarevic

Ahmed Jasarevic

Maintained by Community

Actor stats

0

Bookmarked

2

Total users

1

Monthly active users

3 days ago

Last modified

Categories

Share

Malt Freelancer Scraper

Scrape freelancer profiles from the Malt directory — malt.fr (France), malt.de (Germany) and malt.es (Spain). Get names, headlines, skills, day rates (TJM), location, ratings, missions, availability and profile URLs as clean, structured JSON.

Malt is protected by Cloudflare. This Actor talks to Malt's internal JSON search API (/search/api/profiles) using a Chrome-impersonating HTTP client routed through Apify Proxy's Unblocker group, so it returns data without a browser, DOM scraping or a third-party anti-bot service.

What it does

  • Searches Malt's freelancer directory by keyword/role per selected country domain.
  • Expands each keyword into query variants (react → react freelance, react senior, react remote, …). Malt returns a fixed top-24 per exact query but a different 24 for each query string, so variants are largely disjoint — this is the main coverage lever (a single keyword easily yields 100+ unique profiles).
  • Also repeats each query to surface more of Malt's randomised per-query sample.
  • Returns a flat row per freelancer, ready for CSV/Excel/Sheets export.
  • Optionally enriches each profile with spoken languages, experience level, category/sub-category, description and availability — fetched in parallel.
  • Deduplicates across keywords, query variants, repetitions and domains.
  • Handles the platform aborting event so a stopped run ends quickly.

Input

FieldTypeDescription
searchTermsstring[]Required. Skills/roles to search (e.g. react, data scientist).
locationsstring[]Optional location filter. Note: Malt's guest API currently ignores it and returns the same randomised sample.
domainsstring[]Which sites to search: fr, de, es. Default fr.
maxItemsintegerMax freelancers to save. Default 100.
expandWithVariantsbooleanExpand each keyword into query variants (the main coverage lever). Default true.
variantModifiersstring[]Words appended to each term when expanding (e.g. senior, remote). Default: freelance, senior, expert, junior, lead, remote, consultant, indépendant.
maxRepetitionsintegerTimes to repeat each query to surface more of Malt's randomised sample (1–30). Default 10. Stops early once a query stops yielding new profiles.
scrapeProfileDetailsbooleanFetch each profile page in parallel for languages/experience/category/description. Billed as an extra profile-detail event.
maxConcurrencyintegerParallel search requests (1–8). Default 5.
category, speciality, businessSector, experienceLevel, languagestringOptional filters passed to Malt's search.
minDayRate, maxDayRateintegerOptional day-rate range.
proxyobjectApify Proxy config. Defaults to the UNBLOCKER group.

Coverage note. Malt's public guest API ignores paging, sorting and location, and returns a fixed top-24 per exact query. The reliable way to collect many freelancers is to vary the query string: the Actor appends variantModifiers to each term (and can also repeat a query), which yields largely-disjoint result sets. Disable expandWithVariants if you want a strict exact-match search.

Example input

{
"searchTerms": ["react", "data scientist"],
"domains": ["fr"],
"maxItems": 100,
"expandWithVariants": true,
"scrapeProfileDetails": false
}

Output

Each item in the default dataset contains (profile-detail fields are only present when scrapeProfileDetails is enabled):

name, firstName, lastName, headline, skills, certifiedSkills, dayRate, dayRateCurrency, dayRateFormatted, dayRateVisibility, city, country, countryCode, locationType, rating, missionsCount, recommendationsCount, appraisalsWithRatesCount, badges, availabilityStatus, availabilityFrequency, languages, experienceLevel, category, subCategory, description, photoUrl, profileUrl, sourceDomain, searchTerm, searchLocation, scrapedAt.

Example output item

{
"name": "Sébastien D.",
"headline": "Développeur Front-End Senior | React | TypeScript",
"skills": ["React.js", "Next.js", "TypeScript", "JavaScript"],
"dayRate": 600,
"dayRateCurrency": "EUR",
"city": "Rennes",
"country": "France",
"countryCode": "FR",
"rating": 5,
"missionsCount": 4,
"profileUrl": "https://www.malt.fr/profile/sebastienD",
"sourceDomain": "fr",
"searchTerm": "react",
"scrapedAt": "2026-10-12T13:30:00.000Z"
}

How it works

  1. Builds the query list: each keyword, plus (by default) one query per variant modifier (e.g. react senior), per domain.
  2. Calls GET https://www.malt.{fr|de|es}/search/api/profiles?q=<query> with impit (Chrome TLS impersonation) through Apify Proxy's UNBLOCKER group, retrying transient 403/429/5xx and Cloudflare HTML challenges.
  3. Repeats each query up to maxRepetitions times (sequentially, since concurrent draws return the same sample), stopping after three consecutive draws add nothing new.
  4. Normalizes the JSON response and pushes one item per freelancer as soon as it is found.
  5. Optionally fetches each public profile page and decodes the embedded Nuxt payload for extra fields.

Pricing

This Actor supports pay-per-event (PPE) monetization. Enable it and define the events in Apify Console → your Actor → Publication → Monetization:

EventCharged whenSuggested price
apify-actor-startOnce per run (synthetic, automatic).$0.00005
apify-default-dataset-itemPer freelancer written to the dataset (synthetic, automatic).$0.001
profile-detailPer profile page fetched when scrapeProfileDetails is enabled (custom).$0.002

So the base per-freelancer price stays cheap, and the heavy full-details mode costs extra per profile. If pay-per-event is not enabled, the Actor.charge calls are a safe no-op. The Actor respects the run's maximum cost and stops charging/working once the limit is reached.

Proxy & cost

Cloudflare blocks datacenter IPs and unsupported regions from Malt, so the Actor defaults to the Apify Proxy Unblocker group — the piece that makes requests succeed. Unblocker is billed in units (10 units per successful request) and/or residential transfer; see Apify Proxy pricing. You can point the proxy input at a different Apify Proxy group or turn it off if you have another working route.

Only publicly available freelancer data is collected. Use it responsibly and in line with Malt's terms of service.