How to Find WhatsApp Business Numbers for B2B Outreach

WhatsApp business numbers are not a field on any public directory. The map listing shows a phone number and says nothing about whether it is on WhatsApp. The one place a business declares its WhatsApp number is a click-to-chat link on its own website, and that link is what an extractor can read. Below: the three link formats, how to pull the numbers out of a city-wide list with two API calls per business, the four cases that return nothing, and how to message the results without losing the account.

Why the listed phone number is not a WhatsApp number

In markets where WhatsApp is the default channel, restaurants take bookings on it, clinics confirm appointments on it and trades quote jobs on it, while the landline on the map listing goes to a desk. The listing gives you phone as displayed locally and phone_e164 in international format. Neither field tells you whether that line has a WhatsApp account, and many businesses run WhatsApp on a separate mobile that is never printed on the listing.

The only reliable declaration is the one the business makes itself: a WhatsApp link on its website, put there so customers can reach it. Everything below reads that link and nothing else. A listed phone number that happens to be on WhatsApp is not returned as one, because nothing in the data proves it.

What a click-to-chat link looks like

WhatsApp publishes a URL format that opens a chat with a given number. Businesses paste it into a button, a floating icon or a plain text link. Three shapes are in use, and all of them carry the number in the URL itself:

Link shapeExampleWhere you usually see it
Short linkhttps://wa.me/971501234567Buttons and footers; the most common form
Long linkhttps://api.whatsapp.com/send?phone=971501234567&text=HelloOlder sites and prefilled-message buttons
App schemewhatsapp://send?phone=971501234567Mobile-first sites and some chat plugins

The number is written in international format with no plus sign, spaces or leading zeros, because that is what WhatsApp requires. A number found in a click-to-chat link is therefore already normalised, already tied to a WhatsApp account, and was placed there deliberately by the business. The format is documented in the WhatsApp help centre.

A phone number in the page text tells you nothing about WhatsApp. It might be a landline, a fax line, or a mobile the owner keeps private.

Finding the number by hand

For a dozen contacts, open each business website and look in four places:

  1. The floating chat icon in a bottom corner. Hover over it, or right-click and copy the link address. If the link starts with wa.me or api.whatsapp.com, the number is in it.
  2. The contact page. Many sites list "WhatsApp" as a separate line next to the phone and email, usually as a link.
  3. The footer and header bar, where a WhatsApp icon often sits beside the social icons.
  4. The page source. Search for wa.me and phone=; this also catches links hidden behind an image.

Record the number together with the page URL you found it on. When a recipient asks where you got their number, the answer should be a URL, not a guess.

How to find WhatsApp business numbers with an API

Past a few dozen businesses the manual route stops being worth the time. The machine version has the same three steps: get a list of businesses with their websites, fetch each website, extract the number from any click-to-chat link found there. With Locomint that is two calls per business.

Start with a search, and write the location as "City, Country". In our canary runs a bare "Warsaw" resolved to Warsaw, Indiana.

curl "https://api.locomint.io/v1/places/search?q=dental%20clinic&location=Dubai,%20United%20Arab%20Emirates&limit=50" \
  -H "X-API-Key: $LOCOMINT_KEY"

Each result carries a place_id, the listed phone, and a website where the business has one. For every result with a website, request the full record. The details endpoint fetches the homepage, follows one hop to the contact page when the homepage gave no email or WhatsApp link, and fills an enrichment block. The field you want is enrichment.whatsapp, an E.164 number such as +971501234567.

import httpx

API = "https://api.locomint.io/v1"
headers = {"X-API-Key": "lm_free_your_key_here"}

with httpx.Client(base_url=API, headers=headers, timeout=30) as client:
    search = client.get("/places/search", params={
        "q": "dental clinic",
        "location": "Dubai, United Arab Emirates",
        "limit": 50,
    }).json()

    leads = []
    for summary in search["data"]:
        if not summary.get("website"):
            continue
        place = client.get(f"/places/{summary['place_id']}").json()
        enrichment = place.get("enrichment") or {}
        if enrichment.get("whatsapp"):
            leads.append({
                "name": place["name"],
                "whatsapp": enrichment["whatsapp"],
                "listed_phone": place.get("phone"),
                "website": place.get("website"),
                "status": enrichment.get("website_status"),
            })

    for lead in leads:
        print(lead)

The number is taken from the first click-to-chat link on the page, never from the listed phone. A leading 00 or a missing plus sign in the link is corrected before you see it, so the value is always a plus sign followed by digits. The enrichment is cached per website for 30 days: re-running the same city next week costs one credit per details call as before, but re-crawls nothing. Pass refresh=true to force a new crawl, at one extra credit.

Practical tip: filter on website before fetching details, because a business with no website cannot publish a click-to-chat link and its details call would return website_status: "no_website" for a credit. The arithmetic on the free plan: a 50-place search costs 50 credits, details for every result would cost 50 more, details for only the results with a website costs one credit per website. With 200 credits a month, that filter is what lets you run two or three cities instead of one.

Extracting numbers from websites you already have

If the company list already sits in your CRM and you only need the WhatsApp column, skip the search. The website extraction endpoint takes up to 20 page URLs per call and returns the readable text of each page together with the same contact block: emails, socials, whatsapp, contact_form_url and tech_stack.

import httpx

resp = httpx.post(
    "https://api.locomint.io/v1/websites/extract",
    headers={"X-API-Key": "lm_free_your_key_here"},
    json={"urls": ["https://example.com/", "https://example.com/contact"],
          "output": "text"},
    timeout=60,
)
for row in resp.json()["data"]:
    print(row["status"], row.get("whatsapp"), row.get("emails"))

Pass the homepage and the contact page as separate URLs when you know both. It costs two credits and catches the case where the WhatsApp button exists only on the contact page. The row status explains an empty result: thin means the page is rendered client-side and carried almost no text, parked means the domain shows a registrar page, unreachable means the server did not answer in time, and blocked means the site refused the request and was not retried. Every URL must be a full http or https address with a real host; one bare domain such as example.com in the list fails the whole call with a 400 and code invalid_request. A batch that does not finish within 90 seconds returns 504 with code timeout and charges nothing; send fewer URLs.

What the extractor cannot see

Four cases return no number for a business that does use WhatsApp, and each has a different signature in the response.

  • Chat widgets injected by JavaScript after the page loads. The extractor reads the HTML as the server sends it and does not run scripts, so the number exists but only a browser would see it. website_status is ok and whatsapp is null.
  • A number printed as an image, or typed as plain text without a link. Nothing proves it is on WhatsApp, so it is not reported as one. Same signature as above.
  • Sites that answer a plain request with a block. One US contractor's site returned a 403 from its firewall on the first request; Locomint treats that as a challenge, puts the host into a cooldown and does not retry. website_status comes back unreachable. The same status covers a site that did not answer within the 12-second crawl budget.
  • Stale links. A business that swaps its sales handset leaves the old wa.me link on the site for months. Expect a share of dead numbers and remove them when a message fails to deliver.

The share of websites carrying a click-to-chat link varies by country and category. Measure it with one 50-place search before planning a campaign around it.

Running WhatsApp outreach without getting blocked

WhatsApp is a conversation channel, not a broadcast channel, and the platform enforces that. Accounts that send many identical first messages to people who have not saved the number get reported, and reported accounts get restricted. Rules that keep an account alive:

  • Send from a WhatsApp Business account with a completed profile: real company name, address, website and a description. Recipients check it before they reply.
  • Write each first message for the business you are writing to. Name the business, say in one sentence why you are messaging, and ask one question. Two or three lines is plenty.
  • Send in small batches, spaced out, during the recipient's working hours. A person can send twenty considered messages an hour; a script that sends two hundred in a minute looks exactly like what it is.
  • Stop immediately when someone asks you to, and keep a suppression list so the number is never contacted again from any account.
  • Do not use unofficial bulk-sending tools. They breach the platform terms and are the most common reason numbers are permanently banned.

The legal side depends on where the recipient is. Business-to-business contact points that a company publishes for the purpose of being contacted sit on firmer ground than personal mobiles, and many countries still require that you identify yourself and honour an opt-out. This is not legal advice; the article on whether web scraping is legal covers the frameworks that apply to collecting the data in the first place.

Where to start this week

Pick one category and one city where WhatsApp is the default channel, for example "real estate agency" in "Lagos, Nigeria" or "dental clinic" in "Dubai, United Arab Emirates". Run the search with limit=50, fetch details for the results with a website, and count how many came back with enrichment.whatsapp set. That count is your yield for the segment, and it costs at most 100 credits: 50 for the search and one per website.

Then write ten first messages by hand, send them over two days, and read the replies. If the yield and the reply rate justify it, the paid plans on the pricing page raise the monthly credits without changing a line of the code above. The free plan's 200 credits cover the experiment, and a key from the signup page works immediately with no card.

Frequently asked questions

Is the listed phone number the same as the WhatsApp number?

Often, but not reliably. Many businesses run WhatsApp on a separate mobile line, a shared sales handset, or a number that is never printed on the map listing. The only number you can be sure is on WhatsApp is the one the business put inside a click-to-chat link on its own website, which is what the enrichment.whatsapp field returns.

Why does the API return no WhatsApp number for a business that clearly uses WhatsApp?

The link may sit behind a chat widget that is injected by JavaScript after the page loads, the number may only appear as an image or a plain phone line, or the site may not have been reachable within the crawl budget. Check enrichment.website_status; if it is ok and whatsapp is still empty, the site does not publish a click-to-chat link in its HTML.

Can I message these numbers with a bulk tool?

Unsolicited bulk messaging violates WhatsApp's own terms and gets numbers banned quickly, and in many countries it also breaks electronic marketing rules. Send individual, relevant first messages from a WhatsApp Business account, identify yourself, and stop when asked. Check the rules where your recipients are.