# Leboncoin Scraper — France Classifieds Listings | $3/1K (`bovi/leboncoin-listings`) Actor

Extract public Leboncoin listings with prices, locations, seller details, images, and category attributes. Run with searchText or a search URL; use Apify Residential proxy in FR for reliable access. Pricing: $0.003 per dataset item on the Free plan.

- **URL**: https://apify.com/bovi/leboncoin-listings.md
- **Developed by:** [Vitalii Bondarev](https://apify.com/bovi) (community)
- **Categories:** E-commerce, Lead generation, MCP servers
- **Features:** Limited permissions
- **Stats:** 24 total users, 5 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.91 / 1,000 listings

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

## Leboncoin Listings Scraper for France

Extract structured public listings from Leboncoin.fr, including prices, locations, seller details, images, and category-specific attributes for French market, real-estate, and vehicle research. Search by keyword or a Leboncoin search URL and export the dataset as JSON or CSV.

- Compare real-estate listings using surface, rooms, DPE, GES, and GPS fields.
- Analyze vehicle pricing with brand, model, mileage, fuel, gearbox, and registration year.
- Filter private or professional sellers and capture seller details, SIREN, store IDs, and phone availability.
- Research markets and competitors with category, location, price, and seller filters.
- Export structured records through the Apify dataset; the Actor needs the Apify Residential proxy (FR), which is the default setting.

### What you get

The Actor supports keyword searches with filters or a Leboncoin search URL. It reads Leboncoin’s `__NEXT_DATA__` and `/_next/data` routes and normalizes records, including `parse_confidence` and `warnings`. When the source does not provide a value, the corresponding field is `null`; list fields can be empty.

| Field family | Fields | Type | What it contains |
|---|---|---|---|
| Listing identity | `ad_id`, `title`, `description`, `ad_type`, `url` | string | Identifier, title, body, type, and source URL; `description` can be `null` |
| Pricing | `price`, `price_cents`, `price_currency`, `old_price`, `price_dropped`, `monthly_price` | number, string, boolean | EUR price fields; `old_price` and `monthly_price` can be `null` |
| Taxonomy | `category`, `category_id`, `subcategory` | string | Category information; `subcategory` can be `null` |
| Location | `location_city`, `location_region`, `location_region_id`, `location_department`, `location_department_id`, `location_zipcode`, `location_lat`, `location_lng` | string, number | Location hierarchy and coordinates; source-dependent location values can be `null` |
| Dates | `published_date`, `index_date`, `expiration_date` | ISO 8601 string | Listing lifecycle dates; `expiration_date` can be `null` |
| Seller | `owner_type`, `owner_name`, `owner_store_id`, `owner_user_id`, `owner_siren`, `has_phone` | string, boolean | Seller type, identity, store details, SIREN, and phone availability; source-dependent seller values can be `null` |
| Media | `images`, `image_count`, `thumbnail` | array of strings, integer, string | Image URLs and counts; `images` can be empty and `thumbnail` can be `null` |
| Attributes | `attributes`, `attributes_map` | array of objects, object | Full attributes and flat key-value map; `attributes` can be empty |
| Real estate | `real_estate_type`, `surface_m2`, `rooms`, `bedrooms`, `energy_rate`, `ges` | string, number, integer | Property type, size, rooms, DPE, and GES; these fields can be `null` |
| Vehicles | `vehicle_brand`, `vehicle_model`, `mileage`, `fuel`, `gearbox`, `registration_year` | string, integer | Vehicle specifications; these fields can be `null` |
| Status and provenance | `urgency_level`, `is_boosted`, `status`, `parse_confidence`, `warnings`, `source`, `scraped_at` | integer, boolean, string, number, array of strings, ISO 8601 string | Flags, extraction quality, source path, and scrape time; `warnings` can be empty |

`fuel` and `gearbox` are raw Leboncoin codes (for example `"2"`); the readable labels (for example "Diesel", "Automatique") are in `attributes[].value_label`. `vehicle_model` can carry suffixes such as `model_all` (for example `Q2, model_all`).

The dataset includes three preset views: **Listings Overview**, **Real Estate**, and **Vehicles**.

### Sample output

The sample below is shortened by omitting nonessential fields. The values shown are copied from one real dataset record.

```json
{
  "ad_id": "3289883176",
  "title": "AUDI Q2 Q2 30 TDI 116 S tronic 7 Sport Entretien Complet",
  "description": null,
  "price": 15990,
  "price_currency": "EUR",
  "price_cents": 1599000,
  "category": "Voitures",
  "location_city": "Sarlat-la-Canéda",
  "owner_type": "pro",
  "owner_name": "TRANSAKAUTO SARLAT",
  "has_phone": true,
  "vehicle_brand": "Audi",
  "vehicle_model": "Q2, model_all",
  "mileage": 127000,
  "registration_year": 2019,
  "parse_confidence": 1,
  "warnings": [],
  "source": "searchData.ads"
}
```

### Pricing

The current billing model charges per event.

`apify-actor-start` is charged once per GB of run memory, with a minimum of one event. `apify-default-dataset-item` represents one scraped listing with all fields.

You pay only for the events listed below. This Actor does not use the Pay per event + usage option, so the platform usage of your runs (compute, proxy traffic and storage) is not billed to you separately. The run also records a `listing-item` event per row; it has no price and costs nothing.

| Apify plan | `apify-actor-start` | `apify-default-dataset-item` |
|---|---:|---:|
| Free plan | $0.00005 | $0.003 |
| Silver plan | $0.000049 | $0.00294 |
| Gold plan | $0.0000485 | $0.00291 |
| Platinum plan | $0.000048 | $0.00288 |
| Diamond plan | $0.0000475 | $0.00285 |
| Bronze plan | $0.0000495 | $0.00297 |

Worked examples at the Free-plan rate, before the start event:

| Volume on the Free plan | Dataset item fee |
|--------|-----------------:|
| 100 listings | 100 × $0.003 = $0.30 |
| 1,000 listings | 1,000 × $0.003 = $3.00 |
| 10,000 listings | 10,000 × $0.003 = $30.00 |

The Apify Free plan includes $5 of monthly platform usage credit, which covers about 1,666 results (1,666 × $0.003 = $4.998) after one start event. Free accounts are limited to 10 listings per run, so that volume is reachable only across several runs.

### How to use

1. **Choose** `searchText` with optional filters or a Leboncoin search URL; when accepted, the URL overrides the keyword and individual filters.
2. **Add** a location slug, category ID, price range, seller type, or sort order in keyword mode.
3. **Configure** Apify Residential proxy with country `FR`.
4. **Set** `maxItems` to control the number of listings across pages. Non-paying accounts are capped at 10 listings per run; for paying accounts, `0` means no item limit, and very large result sets stop at 400 pages (about 14,000 listings at 35 per page).
5. **Run** the Actor and inspect `parse_confidence`, `warnings`, and `source`.
6. **Repeat** the run through Apify Schedules.

```json
{
  "searchUrl": "leboncoin.fr/recherche?text=velo&category=2",
  "maxItems": 3,
  "proxyConfiguration": {"useApifyProxy": true, "apifyProxyGroups": ["RESIDENTIAL"], "apifyProxyCountry": "FR"}
}
```

`ownerType` and `sort` apply only in keyword mode; they are ignored when `searchUrl` is used.

Export the dataset as JSON or CSV, or read it through the Apify dataset API.

### Input parameters

| Parameter | What it does | Default |
|---|---|---|
| `searchText` | Keyword search when `searchUrl` is not supplied. Empty search inputs end without listings. | Not set |
| `searchUrl` | Leboncoin search URL; when recognized, it overrides the other search filters. | Not set |
| `locations` | City or region slug in keyword mode; URL location takes precedence in URL mode. | Not set |
| `category` | Numeric Leboncoin category ID in keyword mode. | Not set |
| `priceMin` | Keeps listings at or above the supplied EUR amount. | Not set |
| `priceMax` | Keeps listings at or below the supplied EUR amount. | Not set |
| `ownerType` | Accepts `all`, `private`, or `pro`; only the latter two filter sellers. | `all` |
| `sort` | Accepts `relevance`, `time-desc`, `time-asc`, `price-asc`, or `price-desc`. | `relevance` |
| `maxItems` | Maximum listings across pages. Non-paying accounts are capped at 10 per run; `0` means no item limit for paying accounts, up to the 400-page ceiling. | `100` |
| `proxyConfiguration` | Passes the proxy configuration to Apify; the default uses Apify Residential with country `FR`. | Apify Residential, `FR` |
| `disableUsageStats` | Set to `true` to turn off the run summary described in Usage statistics. | `false` |

### Limits and edge cases

Records reach the dataset after each page's batch is successfully processed and pushed. If a later page fails after earlier pages were pushed, those earlier records remain and pagination stops.

| Condition | What you see | What to do |
|---|---|---|
| Non-paying account sets `maxItems` above 10 (or `0`) | The run is limited to 10 listings and logs the reduction. | Use a paying account for larger runs. |
| A search matches more than about 14,000 listings | Pagination stops at the 400-page ceiling (35 listings per page). | Narrow the search with filters or split it into several runs. |
| Both `searchText` and `searchUrl` are empty | The run reports that there is nothing to search and returns no listings. | Set `searchText` or a Leboncoin search URL. |
| `searchUrl` is not recognized | It is ignored and the Actor falls back to `searchText` and filters. | Use a Leboncoin search URL or provide `searchText`. |
| No listings match | The Actor reports that Leboncoin has no listings for the search. | Widen the keyword, location, category, or price filters. |
| Leboncoin blocks page one after retries | The run reports a block and returns no listings. | Check the proxy configuration and run again. |
| Page one has no usable search data after retries | The run reports no readable search data; this is not confirmed as empty. | Use Apify Residential with country `FR` and run again later. |
| A later JSON page fails or `buildId` changes | The Actor tries HTML, refreshes the build ID when available, and can use an HTML-card fallback. Records may have lower `parse_confidence` and more `warnings`. | Review `source`, `parse_confidence`, and `warnings`. |
| A later page cannot be fetched after fallbacks | Earlier records remain; pagination stops at the failed page. | Review saved records and retry with proxy configured. |

### FAQ

#### How much does it cost to scrape Leboncoin listings?

Each saved listing is one dataset-item event; see Pricing for the rates by plan, the separate start event and worked examples.

#### What happens if my search returns an empty result?

If Leboncoin confirms no matching listings, the Actor reports that the search has no listings. Widen the keyword or filters, or check the `searchUrl` in a browser.

#### Why is the run not working?

Try Apify Residential with country `FR`, then run again. For later-page issues, inspect `parse_confidence`, `warnings`, and `source`.

#### Is it legal to extract Leboncoin listing data?

The Actor extracts public listing data from Leboncoin.fr. Whether collection and use are allowed depends on Leboncoin’s source terms and applicable law for your use case; review those requirements for your intended use.

### Related actors

- [Depop Scraper — Fashion Resale & Sold Items](https://apify.com/bovi/depop-scraper) — related fashion-resale marketplace data.
- [eBay Scraper — Search & Item Details](https://apify.com/bovi/ebay-scraper) — related marketplace search and item-detail extraction.
- [Facebook Marketplace Scraper — No Login | GPS, Photos](https://apify.com/bovi/facebook-marketplace-scraper) — related classifieds data with GPS and photo fields.

### Usage statistics

This Actor creates a small, content-free summary at the end of each run, used only to monitor reliability and improve this Actor. No input values, credentials or scraped data are sent.

A copy of the exact record for your run is saved as `USAGE_STATS` in your own Apify key-value store.

To opt out, set `disableUsageStats` to `true` in the input. Nothing is sent then.

[Full list of collected fields](https://api.apify.com/v2/key-value-stores/v9rgHjMKLDGtHf8tD/records/index.html)

# Actor input Schema

## `searchText` (type: `string`):

Keyword(s) to search on Leboncoin (e.g. 'vélo', 'iphone 14', 'appartement', 'clio 4'). Maps to the 'text' query parameter on leboncoin.fr/recherche. Required unless you paste a Search URL below.

## `searchUrl` (type: `string`):

Paste a complete Leboncoin search URL straight from your browser address bar (e.g. 'https://www.leboncoin.fr/recherche?text=clio\&locations=Bordeaux_33000\&price=2000-8000'). When set, it overrides Search text and the individual filters below — the URL already encodes every filter you picked on the site. Leave blank to use keyword + filters instead.

## `locations` (type: `string`):

City or region slug exactly as it appears in Leboncoin URLs (e.g. 'Paris_75000', 'paris_75', 'ile-de-france_r12', 'lyon_69000'). Open a search on leboncoin.fr, pick a location, and copy the 'locations' value from the address bar. Leave blank for all of France.

## `category` (type: `string`):

Optional Leboncoin numeric category ID to restrict results (e.g. '9' = Real estate, '2' = Cars, '17' = Phones, '31' = Sports & hobbies). Leave blank to search all categories. Find the ID in the 'category' query param of a filtered Leboncoin URL.

## `priceMin` (type: `integer`):

Only return listings priced at or above this amount in euros. Leave blank for no lower bound.

## `priceMax` (type: `integer`):

Only return listings priced at or below this amount in euros. Leave blank for no upper bound.

## `ownerType` (type: `string`):

Restrict to private sellers or professional sellers. Leave as 'all' for both.

## `sort` (type: `string`):

How to order results. 'Relevance' is Leboncoin's default; 'Newest first' is best for monitoring fresh listings; price sorts help find cheapest/most expensive.

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

Maximum number of listings to return across all pages. Set to 0 for all available results (can be thousands — you are charged per listing returned). Default 100.

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

REQUIRED. Leboncoin requires a residential proxy for reliable access — datacenter IPs are not reliable. Use Apify Residential proxy with country France (FR) for the best pass rate. No external proxy account is needed — Apify's built-in residential proxy is billed to your run. Without a residential proxy, runs are rate-limited.

## `disableUsageStats` (type: `boolean`):

See the README Usage statistics section for details.

## Actor input object example

```json
{
  "searchText": "vélo",
  "ownerType": "all",
  "sort": "relevance",
  "maxItems": 100,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ],
    "apifyProxyCountry": "FR"
  },
  "disableUsageStats": false
}
```

# Actor output Schema

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

Dataset containing Leboncoin ad records (ad_id, title, price, price_currency, category, location_city, location_region, url, published_date, owner_type, images, etc.)

# 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 = {
    "searchText": "vélo",
    "maxItems": 100,
    "proxyConfiguration": {
        "useApifyProxy": true,
        "apifyProxyGroups": [
            "RESIDENTIAL"
        ],
        "apifyProxyCountry": "FR"
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("bovi/leboncoin-listings").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 = {
    "searchText": "vélo",
    "maxItems": 100,
    "proxyConfiguration": {
        "useApifyProxy": True,
        "apifyProxyGroups": ["RESIDENTIAL"],
        "apifyProxyCountry": "FR",
    },
}

# Run the Actor and wait for it to finish
run = client.actor("bovi/leboncoin-listings").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 '{
  "searchText": "vélo",
  "maxItems": 100,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ],
    "apifyProxyCountry": "FR"
  }
}' |
apify call bovi/leboncoin-listings --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,bovi/leboncoin-listings"
        }
    }
}
```

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/ErmRlMvhEhWcbe0RJ/builds/QAcsbnSGiLmnToOik/openapi.json
