# Local Business Software Detector: POS, Booking & Ordering (`centorprat/local-business-software-detector`) Actor

Names the software each local business runs from its website or a Google Maps dataset: Toast, Square, ChowNow, OpenTable, Vagaro, Mindbody, NexHealth, ServiceTitan, Jobber, CallRail, Podium and 450 more, plus its vertical, software gaps to pitch and contacts.

- **URL**: https://apify.com/centorprat/local-business-software-detector.md
- **Developed by:** [Centor Prat](https://apify.com/centorprat) (community)
- **Categories:** Lead generation
- **Stats:** 1 total users, 0 monthly users, 0.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $8.50 / 1,000 business profileds

This Actor is paid per event and usage. You are charged both the fixed price for specific events and for Apify platform usage.
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

## Local Business Software Detector: POS, Booking & Ordering

**Find out which software a restaurant, salon, gym, dental office, clinic, contractor, law firm, dealer or
church runs, straight from its website.** Give it websites, or the dataset of any Google Maps scraper run. For
each business you get the vendor behind every system: POS, online ordering vs delivery apps, reservations,
booking, patient scheduling, field-service software, financing, reviews, chat / AI receptionist, call
tracking, CRM and website platform. You also get the business's vertical, **the software gaps worth
pitching**, and public emails, phones and socials.

Built for **sales teams selling into local businesses** (POS, booking, practice, field-service and marketing
software) and the agencies that serve them. "Uses a competitor" and "has a gap" are the two best filters
for outbound, and this gives you both for any Maps search.

### ⚡ What it detects (450+ vendors, 26 categories)

| Category | Examples |
|---|---|
| Online ordering (first-party) | Toast, Square Online, ChowNow, Olo, BentoBox, Popmenu, Owner.com, DoorDash Storefront, Menufy, Slice, HungerRush, white-label ordering on the brand's own subdomain |
| Delivery marketplaces | DoorDash, Uber Eats, Grubhub, Postmates, Caviar, Favor, Deliveroo, Just Eat, Glovo, Wolt |
| Reservations | OpenTable, Resy, Tock, SevenRooms, Yelp Reservations, Toast Tables, TheFork, CoverManager |
| POS (inferred from links) | Toast, Square, Clover, SpotOn, Lightspeed, HungerRush, TouchBistro, Revel, Shift4/SkyTab |
| Booking (beauty, fitness, wellness) | Vagaro, Boulevard, Mindbody, Booker, Fresha, Booksy, GlossGenius, Square Appointments, Mangomint, Zenoti, Phorest, Meevo, Acuity, Calendly, Glofox, Mariana Tek, Momence, WellnessLiving, Jane App, SimplePractice, GoCheckin |
| Patient scheduling & engagement | NexHealth, LocalMed, Zocdoc, Flex Dental, Modento, RevenueWell, Weave, Lighthouse 360, Solutionreach, Adit, Dental Intelligence, Tebra/PatientPop, Vetstoria, PetDesk |
| Field service / shop software | ServiceTitan, Housecall Pro, Jobber, Workiz, ServiceM8, FieldEdge, JobNimbus, AccuLynx, Tekmetric, Shopmonkey, AutoOps |
| Financing & payments | CareCredit, Cherry, Sunbit, Scratchpay, Synchrony, GreenSky, Wisetack, Hearth, Affirm; Stripe, PayPal, Square, LawPay |
| Reviews & reputation | Podium, Birdeye, NiceJob, Broadly, GatherUp, Trustindex, Elfsight, EmbedSocial, BBB seal |
| Chat, texting, AI receptionists | Podium webchat, TrueLark, Smith.ai, tawk.to, Tidio, Ngage, ApexChat, LeadConnector, Gubagoo, WhatsApp |
| Call tracking | CallRail, CallTrackingMetrics, Liine, PatientPrism, Invoca, WhatConverts |
| Marketing & CRM | HubSpot, Mailchimp, Constant Contact, GoHighLevel, Keap, ActiveCampaign, Klaviyo, Yext, Vendasta, Thryv |
| Vertical systems | Clio, Lawmatics (legal) · kvCORE, BoomTown, Sierra, IDX Broker (real estate) · Dealer.com, DealerOn, Dealer Inspire (dealers) · Planning Center, Pushpay, Tithe.ly, Subsplash (churches) · FareHarbor, Peek, Rezdy (tours) · Cloudbeds, SiteMinder (lodging) |
| Website platform | WordPress, Wix, Squarespace, Square Online, GoDaddy, Duda, Webflow, Shopify, BentoBox, SpotHopper, Popmenu, Scorpion, ProSites, Doctor Multimedia... |
| Analytics, ads, accessibility | GA4, Tag Manager, Meta pixel, Google Ads, TikTok, Microsoft Ads, Clarity, Hotjar; UserWay, accessiBe, AudioEye |

**How:** it reads the homepage and up to three key pages (order, menu, book, reserve, appointment, contact,
estimate) and collects every URL the site loads or links to. Local businesses' "Order online", "Book now" and
"Reserve" buttons link straight to their vendor, so the vendor is named with the exact link as evidence. With a
Google Maps dataset, the listing's own order, reserve and booking links count as evidence too.

### 🎯 Gaps it flags, by vertical

| Vertical | Gaps |
|---|---|
| Restaurants | Orders only through delivery apps (15-30% commission) with no direct ordering · no online ordering · no reservations · no gift cards |
| Salons, spas, gyms | No booking software (phone/DM bookings) · generic scheduler instead of industry software · no gift cards |
| Dental, medical, vet | No real-time online scheduling · no patient financing · no review generation · no call tracking |
| Home services, auto repair | No online booking / field-service software · no customer financing · no web chat · no call tracking · no review generation |
| Legal | No live chat or online intake · no call tracking |
| Real estate, churches, tours, lodging | No IDX search · no online giving · no online booking · no direct-booking engine |
| All | No analytics / ad pixels · DIY website builder |

Each gap has a 0-100 score and a plain-English reason; the top three become `pitch`.

### 📥 Input

| Field | What it does |
|---|---|
| `urls` | Business websites or domains, e.g. `["franklinbbq.com", "southaustinbarbershop.com"]` |
| `datasetId` | A Google Maps scraper dataset (or any dataset with a `website` / `url` / `domain` column). Maps name, category, address, phone, rating and reviews are passed through. |
| `verticals` | Keep only some business types (restaurant, beauty, fitness, dental, medical, veterinary, homeServices, autoRepair, autoDealer, legal, realEstate, church, lodging, activities, retail, professional) |
| `requireVendors` | Keep only businesses using any of these, e.g. `["Toast"]` |
| `excludeVendors` | Drop businesses using any of these, e.g. your own product |
| `missingCategories` | Keep only businesses with a gap in these categories, e.g. `["booking"]` or `["onlineOrdering"]` |
| `includeUnreadable` | Also return (unbilled) rows for websites that couldn't be read |
| `concurrency`, `maxItems`, `webhookUrl` | Speed, dataset cap, webhook |

**Example: restaurants in a Maps search that order only through delivery apps**

```json
{ "datasetId": "<your Google Maps scraper dataset>", "verticals": ["restaurant"], "missingCategories": ["onlineOrdering"] }
```

**Example: salons on a competitor's booking software**

```json
{ "datasetId": "<your Google Maps scraper dataset>", "verticals": ["beauty"], "requireVendors": ["Vagaro", "Booksy"] }
```

### 📤 Output (one row per business, shortened)

```json
{
  "businessName": "Güero's Taco Bar",
  "website": "https://gueros.com",
  "vertical": "restaurant",
  "vendors": [
    {"name": "ChowNow", "category": "onlineOrdering", "confidence": "high",
     "evidence": ["https://ordering.chownow.com/order/20310/locations/29264"]},
    {"name": "OpenTable", "category": "reservations", "confidence": "high",
     "evidence": ["https://www.opentable.com/r/gueros-taco-bar-reservations-austin?restref=1347361"]}
  ],
  "software": {
    "websitePlatform": ["WordPress"],
    "onlineOrdering": ["ChowNow"],
    "reservations": ["OpenTable"],
    "pos": ["Toast (POS)"],
    "giftCardsLoyalty": ["Toast gift cards"]
  },
  "websitePlatform": "WordPress",
  "posInferred": ["Toast (POS)"],
  "ordering": {"firstParty": ["ChowNow"], "marketplaces": []},
  "keySystems": ["ChowNow", "OpenTable"],
  "gaps": [{"category": "analyticsAds", "score": 50,
            "why": "No analytics or ad tracking (Google Analytics, Tag Manager, Meta pixel) on the site"}],
  "pitch": ["No analytics or ad tracking (Google Analytics, Tag Manager, Meta pixel) on the site"],
  "emails": ["info@gueros.com", "catering@guerostacobar.com"],
  "phones": ["5124477688"],
  "socials": {"instagram": "https://www.instagram.com/guerostacobar", "facebook": "https://www.facebook.com/gueros"},
  "pagesScanned": 3,
  "auditComplete": true
}
```

With a Google Maps dataset, each row also carries `mapsCategory` and `maps` (title, address, phone, rating,
reviews count, placeId, Maps URL).

### 💰 Pricing (pay-per-event)

- **Business profiled: $0.01** per website read and analysed ($10 per 1,000).
- Free: dataset rows without a website, websites that can't be read, and Maps rows skipped by `verticals`.
- Vendor and gap filters run after the analysis, so every analysed website is billed.

### 💡 Use cases

- **POS and ordering vendors:** restaurants on Toast, Square or Clover, and restaurants paying marketplace
  commission with no direct ordering.
- **Booking software vendors:** salons, spas and studios with no booking software, or on a competitor's.
- **Dental and medical SaaS:** practices without online scheduling, financing or review tools.
- **Home-services software and financing:** contractors with no field-service software, financing or chat.
- **Local marketing agencies:** businesses with no analytics or ads tracking, a DIY website, or no review generation.
- **Enrich a Maps search:** add a full software stack and contacts to every place in one pass.

### 🚀 Ready-made tasks

- [Restaurant POS & Online Ordering Detector](https://apify.com/centorprat/local-business-software-detector/examples/restaurant-pos-online-ordering-detector)
- [Salon & Spa Booking Software Detector](https://apify.com/centorprat/local-business-software-detector/examples/salon-spa-booking-software-detector)
- [Dental Practice Software Detector](https://apify.com/centorprat/local-business-software-detector/examples/dental-practice-software-detector)
- [Home Services Software Detector (ServiceTitan, Jobber, Housecall Pro)](https://apify.com/centorprat/local-business-software-detector/examples/home-services-software-detector)

### 🔌 API, Standby and agents

**Instant lookup (Standby):**

```bash
curl "https://centorprat--local-business-software-detector.apify.actor/?url=franklinbbq.com&token=<YOUR_APIFY_TOKEN>"
curl "https://centorprat--local-business-software-detector.apify.actor/?urls=gueros.com,grandoaksdentistry.com&token=<YOUR_APIFY_TOKEN>"
```

**Python**

```python
from apify_client import ApifyClient
client = ApifyClient("<YOUR_APIFY_TOKEN>")
run = client.actor("centorprat/local-business-software-detector").call(run_input={"urls": ["franklinbbq.com"]})
for b in client.dataset(run["defaultDatasetId"]).iterate_items():
    print(b["businessName"], b["vertical"], b["keySystems"], b["pitch"])
```

**JavaScript**

```js
import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: '<YOUR_APIFY_TOKEN>' });
const run = await client.actor('centorprat/local-business-software-detector').call({ urls: ['franklinbbq.com'] });
const { items } = await client.dataset(run.defaultDatasetId).listItems();
```

**MCP**

```json
{
  "mcpServers": {
    "apify": {
      "url": "https://mcp.apify.com/?tools=actors,docs,centorprat/local-business-software-detector"
    }
  }
}
```

**Claude Code:** `claude mcp add --transport http apify "https://mcp.apify.com/?tools=actors,docs,centorprat/local-business-software-detector" --header "Authorization: Bearer <YOUR_APIFY_TOKEN>"`

### ❓ FAQ

**How is the POS known?** It's inferred, and labelled so (`confidence: "inferred"`). A restaurant whose ordering
or gift-card links go to Toast is almost always on Toast POS, and the same goes for Square and Clover. When no
ordering or payment link exposes it, the POS isn't reported.

**Does it scrape Google Maps?** No. Run any Google Maps scraper first and pass its dataset. This Actor reads the
businesses' own websites (and the links in the Maps rows).

**What about white-label systems?** "Order online" or "Book now" buttons that go to the business's own subdomain
(order.brand.com, book.brand.com) are reported as white-label ordering or booking, not as a gap.

**Can a gap be wrong?** A gap means "not found on the website". A business can still take bookings by phone or
use a system it doesn't link. The `why` text says exactly what was and wasn't found; treat gaps as signals for
outreach, not facts about the business.

**How fast?** About 1-3 seconds per website, 10 in parallel by default (up to 20).

**Which countries?** Any. Vendor packs are strongest for the US, UK, Canada and Australia, and include Europe's
TheFork, CoverManager, Glovo, Just Eat and Wolt.

**Is it legal?** It reads public web pages like a browser. No login, no private data, no form submissions.

### 📜 Data & attribution

Reads only public business websites (and the dataset you provide). Vendor names are trademarks of their owners
and are reported only as detected integrations.

### 🔗 Related actors

- [Google Maps Leads + Website Audit for Agencies](https://apify.com/centorprat/google-maps-leads-website-audit): local businesses from Google Maps audited for website, Google profile, reviews, booking and tracking gaps.
- [Shopify App Detector: Tech Stack, Pixels & Theme](https://apify.com/centorprat/shopify-app-detector): every app a Shopify store runs, with evidence, estimated app spend and change tracking.
- [Domain Lookup API - DNS, MX, SPF, Tech & Contact Emails](https://apify.com/centorprat/domain-lookup-dns-mx-email): DNS + live homepage → IPs, MX/SPF, tech, socials and public contacts per domain.

# Actor input Schema

## `urls` (type: `array`):

Websites or domains, e.g. \["franklinbbq.com", "southaustinbarbershop.com"]. One business per entry.

## `datasetId` (type: `string`):

Pick the dataset of a Google Maps scraper run (or any dataset with a website / url / domain column). The Maps category sets the vertical, the Maps listing links (order, reserve, book) add evidence, and name, address, phone, rating and review count are passed through. Read-only.

## `verticals` (type: `array`):

Keep only these business types: restaurant, beauty, fitness, dental, medical, veterinary, homeServices, autoRepair, autoDealer, legal, realEstate, church, lodging, activities, retail, professional, other. With a Maps dataset, rows whose category is another vertical are skipped before the site is read (free).

## `requireVendors` (type: `array`):

Return only businesses running at least one of these, e.g. \["Toast"] or \["Vagaro", "Mindbody"]. Case-insensitive. Use it to build a competitor's customer list from any Maps search.

## `excludeVendors` (type: `array`):

Leave out businesses that already run one of these, e.g. your own product.

## `missingCategories` (type: `array`):

Return only businesses with at least one of these gaps: onlineOrdering, reservations, booking, practiceSoftware, fieldService, financing, reviewsReputation, chatMessaging, callTracking, giftCardsLoyalty, analyticsAds, websitePlatform, churchSoftware, realEstate, toursActivities, lodging.

## `includeUnreadable` (type: `boolean`):

Adds a row (not billed) for each site that timed out or blocked the read, so your list stays complete.

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

Safety cap when reading a dataset.

## `concurrency` (type: `integer`):

How many websites are read at once.

## `webhookUrl` (type: `string`):

If set, the results are POSTed here as JSON (Zapier / Make / n8n / your CRM).

## Actor input object example

```json
{
  "urls": [
    "gueros.com",
    "southaustinbarbershop.com",
    "grandoaksdentistry.com"
  ],
  "includeUnreadable": false,
  "maxItems": 1000,
  "concurrency": 10
}
```

# Actor output Schema

## `businesses` (type: `string`):

One row per business website: name, vertical, every detected vendor (name, category, evidence), software grouped by category, website platform, POS (inferred), online ordering vs delivery marketplaces, key systems, software gaps with scores and pitch lines, public emails, phones and socials, and Google Maps fields when the input was a Maps dataset.

# 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 = {
    "urls": [
        "gueros.com",
        "southaustinbarbershop.com",
        "grandoaksdentistry.com"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("centorprat/local-business-software-detector").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 = { "urls": [
        "gueros.com",
        "southaustinbarbershop.com",
        "grandoaksdentistry.com",
    ] }

# Run the Actor and wait for it to finish
run = client.actor("centorprat/local-business-software-detector").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 '{
  "urls": [
    "gueros.com",
    "southaustinbarbershop.com",
    "grandoaksdentistry.com"
  ]
}' |
apify call centorprat/local-business-software-detector --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,centorprat/local-business-software-detector"
        }
    }
}
```

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/oxYzcu0Bn6jGUyh0X/builds/CYsBHiNjzWZFubOl4/openapi.json
