BizBuySell Scraper - Businesses for Sale, Franchises & Brokers avatar

BizBuySell Scraper - Businesses for Sale, Franchises & Brokers

Pricing

from $1.50 / 1,000 results

Go to Apify Store
BizBuySell Scraper - Businesses for Sale, Franchises & Brokers

BizBuySell Scraper - Businesses for Sale, Franchises & Brokers

From $1.5/1K. Extract business-for-sale and franchise listings from bizbuysell.com with financials, full descriptions, photos, and broker contact details. Search by filters or paste BizBuySell URLs directly. Returns 30+ structured fields per listing, ready for CRMs, deal pipelines, or spreadsheets.

Pricing

from $1.50 / 1,000 results

Rating

0.0

(0)

Developer

Abot API

Abot API

Maintained by Community

Actor stats

2

Bookmarked

149

Total users

60

Monthly active users

a day ago

Last modified

Share

BizBuySell Scraper: Business-for-Sale & Franchise Listings

BizBuySell Scraper turns BizBuySell into structured deal data. Pull business-for-sale and franchise listings with financials, the full description, photos, and the listing broker's name and phone number where the listing shows them. Run it by filters (industry category, location, listing type, asking price, cash flow, gross revenue, keyword, sort) or by pasting BizBuySell search, category, or listing URLs. Every result is a flat JSON record with 30+ fields, ready to drop into a CRM, a deal pipeline, or a spreadsheet, and to export as JSON, CSV, or Excel, or read through the API.

Why This Scraper?

  • 30+ fields per listing, including the broker contact block (name, phone, brokerage, license where shown), which most quick scrapes skip.
  • Full financials: asking price, cash flow (SDE), gross revenue, EBITDA, inventory, FF&E, real estate (and whether it is included in the asking price), established year, and employees, plus everything else the listing discloses, kept verbatim in a detailsRaw map.
  • Deal-context narrative fields where the listing includes them: facilities, growth and expansion notes, competition, reason for selling, and support and training terms.
  • Two ways in: a filter search (category, location, listing type, price, cash flow, gross revenue, keyword, sort) or paste any BizBuySell search, category, or listing URL directly.
  • Auto-pagination and dedup, plus a fast lean mode that skips detail pages when you only need the search-card fields.
  • Built for schedules. Incremental mode returns only new and changed listings on recurring runs, and Resume continues one interrupted run without paying twice for listings you already have.

Use Cases

  • Business brokers and M&A advisors: pull comparable active listings by category and region to price a new engagement.
  • Buyers and searchers: build a filtered watchlist by industry, price range, and cash flow, and monitor it on a schedule for new matches.
  • Franchise buyers: track franchise-for-sale listings alongside their broker contact details.
  • Deal sourcing for search funds and small PE: build an acquisition target list with financials attached, ready for a CRM or a spreadsheet.
  • Lead generation teams: collect broker names, phone numbers, and brokerages tied to active listings in a given market.

Data You Get

Sample shape: values are illustrative placeholders, not from a live listing.

FieldExample
id"0000000"
url"https://www.bizbuysell.com/business-opportunity/sample-business/0000000/"
title"Established Sample Business"
category"Sample Category > Subcategory"
listingType"established"
city / state"Sample City" / "FL"
askingPrice250000
priceReducedfalse
cashFlow95000
grossRevenue480000
ebitdanull
inventory / ffe20000 / 35000
realEstate / realEstateIncluded"Leased" / false
establishedYear / employees2018 / "4 FT"
reasonForSelling"Retirement"
franchise"No"
fullDescriptionfull listing text (when fetchDetails is on)
brokerName / brokerPhone / brokerageName"Jane Doe" / "+15550000000" / "Sample Brokerage"
datePosted"January 1, 2026"
isVerifiedtrue
detailsRawevery disclosed fact, verbatim, keyed by field name
sourceUrlthe search or listing URL that produced this record

Broker name and phone are present only on listings that BizBuySell itself shows them on (broker-listed businesses). Listings posted directly by owners route contact through a form and expose neither. In incremental mode, records also carry changeType, changedFields, firstSeenAt, and lastSeenAt.

Extra listing attributes.

Each listing also carries location, stateCode, categoryFinal, fetchedAt, and these flags and codes read straight from the search page: recentlyAdded and recentlyUpdated (true/false, BizBuySell's own "recently added / updated" badges) and leaseRateDuration (BizBuySell's numeric lease-rate code, not decoded). auctionStartDate and auctionEndDate are filled only for auction listings and are null otherwise. BizBuySell's search results and listing pages carry no listed, last-updated or lease-expiration date and no full category path (checked live, October 2026), so those are not offered; datePosted is filled when a listing page shows one. fetchedAt is ignored by incremental change detection. These fields cost nothing extra.

Dataset views. The Console dataset has three views: Listings (overview, includes detailsRaw), Detail & broker (financials, description, broker block) and Changes (changeType, changedFields for incremental runs).

How to Use

  1. Pick a mode: search (filter fields) or url (paste BizBuySell links).
  2. In search mode, fill in keyword, category, location, listing type, price, and cash flow filters as needed. In URL mode, paste one or more search, category, or listing URLs.
  3. Turn Fetch full listing details on for financials, full description, photos, and broker contact, or leave it off for a fast, lean run.
  4. Set Max listings (and, optionally, Max search pages) to bound the run, then click Start. Download the dataset as JSON, CSV, or Excel, or read it through the API.

Basic filter search:

{ "mode": "search", "maxPages": 3, "maxListings": 100 }

Filtered search with financials (the cash flow filter reads the detail page, so fetchDetails is on):

{ "mode": "search", "keyword": "coffee shop", "location": "California", "minAskingPrice": 100000, "maxAskingPrice": 500000, "minCashFlow": 80000, "fetchDetails": true, "maxPages": 5 }

Category and location, cheapest first, lean run:

{ "mode": "search", "category": "restaurants-and-food", "location": "Florida", "sortBy": "price-asc", "maxPages": 3, "fetchDetails": false }

Paste URLs (search page and a specific listing):

{ "mode": "url", "urls": ["https://www.bizbuysell.com/businesses-for-sale/", "https://www.bizbuysell.com/business-opportunity/sample-business/0000000/"], "maxPages": 2 }

URL mode: supported URL shapes

Behaviour change: in URL mode, leaving urls untouched now scrapes one example of each supported list-page shape in the table below (the 8 URLs in the default; the single-listing example appears only in the prefilled example input, and broker-directory URLs are not supported) (previously nothing was scraped without a URL). Pass your own list, or [], to override. Query filters such as ?q= and ?showAssetSale=true are kept on every page (earlier versions dropped them after page 1). Page paths always end in a slash.

ShapeExample
Nationwide listinghttps://www.bizbuysell.com/businesses-for-sale/
Paginated (starts at page N)https://www.bizbuysell.com/florida-businesses-for-sale/2/
Categoryhttps://www.bizbuysell.com/restaurants-and-food-businesses-for-sale/
Location + categoryhttps://www.bizbuysell.com/florida/restaurants-and-food-businesses-for-sale/
Keyword searchhttps://www.bizbuysell.com/businesses-for-sale/?q=Y29mZmVl
Asset-sale filterhttps://www.bizbuysell.com/businesses-for-sale/?showAssetSale=true
Franchise index / sub-categoryhttps://www.bizbuysell.com/franchise-for-sale/low-cost-franchise/
Single listinghttps://www.bizbuysell.com/business-opportunity/<slug>/<id>/ (often refused to automated requests; a warning is logged and no record is produced)
Broker directoryhttps://www.bizbuysell.com/business-brokers/ (not supported: skipped with a warning)

Run it from your code

Python:

from apify_client import ApifyClient
client = ApifyClient("<YOUR_APIFY_TOKEN>")
run = client.actor("abotapi/bizbuysell-scraper").call(
run_input={"mode": "search", "category": "restaurants-and-food", "maxListings": 50})
for listing in client.dataset(run["defaultDatasetId"]).iterate_items():
print(listing["title"], listing["askingPrice"])

JavaScript:

import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: '<YOUR_APIFY_TOKEN>' });
const run = await client.actor('abotapi/bizbuysell-scraper').call({
mode: 'search', category: 'restaurants-and-food', maxListings: 50,
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();

Or connect it to Make, Zapier, n8n, Google Sheets, or webhooks from the Integrations tab.

Resume and recurring updates

Two different things:

  • Resume from a previous run (resumeFromRunId) continues one specific interrupted run: paste its run or dataset ID and the actor skips listings already collected there, so you do not pay twice.
  • Incremental mode (incrementalMode) is for daily or recurring monitoring of the same search. Each listing is classified NEW, UPDATED (with changedFields), UNCHANGED (suppressed and not billed unless emitUnchanged is on), REAPPEARED, or EXPIRED (only after a run that scanned the whole tracked search, and only with emitExpired). State is tracked separately per mode, keyword, category, location, filter (including the max cash flow and max gross revenue filters when set), and fetchDetails setup unless you set a State key; in URL mode it is tracked per URL list. Any returned field changing makes a listing UPDATED, except the priceReduced flag, the recentlyAdded and recentlyUpdated badges (the recently-added / recently-updated badges), the imageUrl thumbnail, the fetchedAt timestamp and the order of images (the site can clear or reshuffle these without the listing changing; a real price change is still caught through askingPrice). Add more with ignoreFieldsForChanges (top-level field names or dotted paths such as detailsRaw.Employees); ignored fields are still returned in the output, and stored baselines are re-compared with the current ignore set so changing it never causes a one-time wave of UPDATED rows. Newly added fields (location, stateCode, categoryFinal, auctionStartDate, auctionEndDate, leaseRateDuration) start being compared only once a baseline has stored them, so the first run after an upgrade does not mark every tracked listing UPDATED.

Send results into your apps (MCP connectors)

Optionally pipe the scraped results into the apps you already use, via Model Context Protocol (MCP) connectors. This is an extra delivery step after the scrape: the Apify dataset is never changed.

What gets written to the connector: a condensed, human-readable summary of each record, not the full JSON. Each item becomes one entry with a title and its key fields flattened to plain text. The complete record always stays in the Apify dataset.

  1. Authorize a connector once under Apify β†’ Settings β†’ Integrations (Notion, Linear, Airtable, or Apify).
  2. Select it in the "Pipe results into your apps" input field. (If the picker is empty, you have not authorized a connector yet.)
  3. For Notion, also set notionParentPageUrl to the page where items should be created.

The connection is mediated by Apify's MCP proxy, so this actor never sees your third-party credentials. Leave the field empty to skip.

Input Parameters

ParameterTypeDefaultDescription
modestringsearchsearch uses the filter fields below; url fetches the URLs you paste.
keywordstring(none)Free-text keyword, e.g. "coffee shop". Leave blank to browse all listings.
categorystring(none)BizBuySell industry category slug, e.g. "restaurants-and-food". Leave blank for all categories.
locationstring(none)US state or region, e.g. "Florida". For one specific city, paste that city's BizBuySell URL in URL mode instead. Leave blank for nationwide.
listingTypestringallall, established, or asset-sale. Applies in search mode only, matched against each listing's own type; not applied in URL mode. Also forms part of the automatically derived incremental state key.
minAskingPriceinteger(none)Only return listings with an asking price at or above this amount.
maxAskingPriceinteger(none)Only return listings with an asking price at or below this amount.
minCashFlowinteger(none)Only return listings whose cash flow (SDE) is at or above this amount. Cash flow lives on the detail page, so enable fetchDetails for this filter to apply.
minGrossRevenueinteger(none)Only return listings whose annual gross revenue is at or above this amount. Also on the detail page, so enable fetchDetails for this filter to apply.
maxCashFlowinteger(none)Only return listings whose annual cash flow is at or below this amount. Applied after parsing; a listing with an unknown value is kept.
maxGrossRevenueinteger(none)Only return listings whose annual gross revenue is at or below this amount. Applied after parsing; a listing with an unknown value is kept.
startUrlsarray(none)Alias of urls for users migrating from other BizBuySell scrapers. When it holds at least one URL it wins over urls (which always carries its example list on the platform) and the run switches to URL mode.
results_wantedinteger(none)Alias of maxListings. When set it wins over maxListings.
max_pagesinteger(none)Alias of maxPages. When set it wins over maxPages.
proxyConfigurationobject(none)Alias of proxy. When set it wins over proxy.
sortBystringdefaultdefault (best match), price-asc, price-desc, newest, or cashflow-desc.
urlsarray8 example URLs (one per supported shape; see URL shapes below)One or more BizBuySell search, category, keyword, asset-sale, franchise, or listing URLs (URL mode). Filter fields are ignored. Pagination starts at the page in the URL and walks forward; query filters such as ?q= and ?showAssetSale=true are kept on every page.
fetchDetailsbooleanfalseOpen each listing page for financials, full description, photos, and broker contact. Adds one request per listing. Leave off for a fast, lean run with just the search-card fields.
maxPagesinteger0Result pages to walk per search or per URL. 0 means no page limit: the walk runs until BizBuySell stops returning new results, or until maxListings is reached.
maxListingsinteger20Stop after this many listings total (0 = the maximum, 100000). This is the main bound on run size and cost; a run never exceeds 100000 listings or 1000 result pages per search or URL.
proxyobjectApify Residential proxy, country USConnection settings. Residential US is recommended; see Plan Requirement. A custom proxy URL is used as-is with no backup connection.
mcpConnectorsarray(none)Optional: send a summary of each listing to apps you authorized under Integrations.
notionParentPageUrlstring(none)Notion connector only: page under which listing pages are created.
maxNotifyListingsinteger50Cap on items written to each connector per run. Does not affect the dataset.
resumeFromRunIdstring(none)Paste a previous run ID or dataset ID to continue one specific interrupted pull without re-scraping listings already collected there.
incrementalModebooleanfalseTurn on for daily or recurring monitoring of the same search. See "Resume and recurring updates" above.
stateKeystring(none)Name an incremental-mode monitoring campaign, or leave empty to derive one automatically from the search and filter setup.
emitUnchangedbooleanfalseIncremental mode only: also return (and bill) listings classified UNCHANGED.
emitExpiredbooleanfalseIncremental mode only: also return (and bill) listings classified EXPIRED, produced only after a run that fully scanned the tracked search.
ignoreFieldsForChangesarray[]Incremental mode only: field names (or dotted paths like detailsRaw.Employees) that never make a listing UPDATED. Still returned in the output.

Output Example

Sample shape: values are illustrative placeholders, not from a live listing.

{
"id": "0000000",
"url": "https://www.bizbuysell.com/business-opportunity/sample-business/0000000/",
"title": "Established Sample Business",
"category": "Sample Category > Subcategory",
"listingType": "established",
"city": "Sample City",
"state": "FL",
"shortDescription": "Short teaser from the search card.",
"fullDescription": "Full listing description text appears here when fetchDetails is on.",
"askingPrice": 250000,
"cashFlow": 95000,
"grossRevenue": 480000,
"ebitda": null,
"inventory": 20000,
"ffe": 35000,
"realEstate": "Leased",
"establishedYear": 2018,
"employees": "4 FT",
"reasonForSelling": "Retirement",
"supportTraining": "2 weeks included",
"financingAvailable": "Yes",
"relocatable": "No",
"homeBased": "No",
"franchise": "No",
"leaseInfo": "$3,500.00",
"facilities": "Home based. Equipment fits in a single van.",
"growthExpansion": "Owner has identified two adjacent territories with no active competitor.",
"competition": "A handful of regional operators, none offering the same turnkey service.",
"realEstateIncluded": false,
"priceReduced": false,
"imageUrl": "https://images.bizbuysell.com/shared/listings/000/0000000/000000-W768.webp",
"images": ["https://images.bizbuysell.com/shared/listings/000/0000000/000000-W768.webp"],
"brokerName": "Jane Doe",
"brokerPhone": "+15550000000",
"brokerageName": "Sample Brokerage",
"brokerProfileUrl": "https://www.bizbuysell.com/business-broker/sample/0000/",
"brokerLicense": "00000000",
"datePosted": "January 1, 2026",
"isVerified": true,
"detailsRaw": { "askingPrice": "$250,000", "cashFlow": "$95,000", "establishedYear": "2018" },
"sourceUrl": "https://www.bizbuysell.com/businesses-for-sale/"
}

Plan Requirement

BizBuySell's edge refuses plain requests that do not come from a residential-quality connection, so this actor needs proxy access. It defaults to Apify Residential proxy, country US, and that is the lane we recommend; a single small test through a datacenter connection also loaded pages, but one run is not enough to recommend it, so do not rely on it. If the selected connection is refused, the actor tries a backup connection, and when it does you will see this in the run log:

The selected connection is unavailable to this run.
Apify free plans do not include residential proxies.
Continuing on a backup connection; some pages may still be unavailable.
For residential access, upgrade at https://apify.com/pricing or supply your own proxy URLs.

followed, if a backup serves pages, by Served over the backup connection (the default connection was unavailable). Apify free plans have no residential proxy, so a paid plan with proxy access is the reliable setup (or supply your own proxy URLs, which are used as-is with no backup). Listing pages opened by fetchDetails and single listing URLs are often refused to automated requests; those fields may stay empty and a warning is logged rather than a silent zero.

FAQ

How much does it cost?

You pay per listing returned. Turning on fetchDetails adds a separate per-listing detail-enrichment charge for the listings it actually enriches (any listing pushed without a successful detail fetch is not charged for details). Current rates (per 1,000 for FREE / BRONZE / SILVER / GOLD tiers): result apify-default-dataset-item $2.20 / $2.00 / $1.80 / $1.50 per 1,000 listings; detail enrichment detail-enrichment $1.50 / $1.20 / $1.00 / $0.80 per 1,000 enriched listings; plus an actor start fee apify-actor-start of $0.05 / $0.04 / $0.03 / $0.02 per start. Platform compute and proxy usage are billed by Apify to your account on top. The Pricing tab is authoritative. Use Max listings to cap the cost of any run.

This actor collects only publicly available listing data. You are responsible for how you use it: follow BizBuySell's terms and the laws that apply to you, and get legal advice if you plan commercial redistribution. Listing text, photos, and broker details may be subject to third-party rights.

Can I get only new or changed listings on a schedule?

Yes. Schedule the actor from the Schedules tab and turn on Incremental mode. Each run then returns only new, updated, and reappeared listings, and unchanged ones are not billed unless you opt in with emitUnchanged.

Why do my cash flow or gross revenue filters let through listings that don't match?

minCashFlow and minGrossRevenue are checked against values that are usually only on the listing detail page. A listing whose value is unknown is kept rather than dropped. Turn on fetchDetails so those values are fetched before the filter is applied; with it off, only listings whose search card shows a lower value are filtered out.

Why did my run return zero or few listings, or fail?

If no results page could be loaded at all, the run now fails with a clear message instead of finishing empty. One of:

  • "The proxy connection was refused for this account, so no page could be read. Your Apify plan does not include proxy access; a paid plan is required: https://apify.com/pricing. If you entered your own proxy URLs, check that their credentials are valid."
  • "No results: residential proxies are unavailable on this run (Apify free plans do not include them), and the backup connection could not load the requested BizBuySell pages. Upgrade at https://apify.com/pricing or supply your own proxy URLs, then try again."
  • "Could not load any results page (the requests failed), so nothing was collected. This is a connection problem, not an empty search. Please try again later."

If some pages were collected first, the run ends early with what it has (and a warning that not enough run time remains for another connection attempt; raise Run options β†’ Timeout for larger jobs). Two input cases fail on purpose: Incremental mode together with Resume from a previous run when that state key already has tracked listings, and a Resume from a previous run value that matches no readable run or dataset.

Can I use it with AI agents or MCP?

Yes. Call it from any Apify integration or MCP client, and use the connector field to push results into Notion, Linear, or Airtable.

πŸ”— Want more leads data?

Pair this actor with these related scrapers from the same team:

πŸ“‡ BizQuest Scraper
Extract business-for-sale, franchise, and asset listings from BizQuest. Search by...
πŸ“‡ BusinessesForSale.com Scraper
From $1.5/1K. Extract businesses and franchises listed for sale on BusinessesForSale.com...
🏠 Crexi Scraper
Scrape crexi.com commercial listings: asking price, cap rate, square footage, units, year...
🏨 LoopNet Scraper
Scrape LoopNet commercial listings across the US, including office, retail, industrial...
🏠 LandWatch
From $1/1k. Scrape land, farm, ranch, and rural property listings from LandWatch.com...
πŸ›’ Flippa Scraper
From $0.80/1K. Scrape Flippa listings with full enrichment, including revenue, profit...

πŸ‘‰ Browse all abotapi scrapers

πŸ’¬ Support & custom scrapers

  • 🐞 Found a bug or a missing field? Open a ticket on the Issues tab. We usually reply within hours.
  • πŸ› οΈ Need another site, extra fields or a private build? Email contact@abotapi.com or message Telegram @abotapi.
  • ⭐ Enjoying it? A quick review on the actor page helps other users find it.