# Tech Stack & WHOIS Lookup: BuiltWith & Wappalyzer Alternative (`devarq/domain-tech-stack-whois-dns`) Actor

Tech stack lookup and domain WHOIS lookup for any list of domains: website technologies (BuiltWith / Wappalyzer alternative), SaaS tools from DNS records, email provider, MX/SPF/DMARC, DNS lookup, domain age, SSL certificate. Domain intelligence from $3 per 1,000 domains.

- **URL**: https://apify.com/devarq/domain-tech-stack-whois-dns.md
- **Developed by:** [Devarq](https://apify.com/devarq) (community)
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 1 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.40 / 1,000 domain profiles

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

### What is Tech Stack & WHOIS Lookup?

**Tech Stack & WHOIS Lookup** is a domain lookup API that returns a company's **tech stack**, the **SaaS tools it verified in DNS**, its **email provider and email security**, **WHOIS registration**, **DNS records**, **hosting** and **SSL certificate** for any list of domains, in one run, from **$3 per 1,000 domains**.

Paste domains, website URLs or company email addresses and get one clean row per domain as **JSON, CSV or Excel**. There's no BuiltWith or Wappalyzer account to buy, no proxy to configure and no browser to run.

The easiest way to try it: click **Try for free**, then **Start** with the three prefilled domains. About 10 seconds later you'll have stripe.com, shopify.com and notion.so profiled. Apify's free plan includes $5 of credit every month, which covers **about 1,600 domains**.

![Tech stack lookup results for stripe.com, shopify.com and notion.so in the Overview table](https://api.apify.com/v2/key-value-stores/sVImVssQJMukOyxVQ/records/domain-tech-stack-lookup-overview.png?signature=GvLFDmNFAyfRy4PnV77g)

#### What data can you extract?

- **Website technologies**: CMS, ecommerce platform, frameworks, analytics, tag managers, CDN, web server, hosting, payments, marketing automation and live chat, each with version, confidence and the evidence behind it
- **SaaS tools verified in DNS**: verification records companies publish for Salesforce, Microsoft 365, Atlassian, DocuSign, Zoom, OpenAI, Stripe and many more. Page-only detectors can't see these
- **Email provider and security**: Google Workspace, Microsoft 365 and others from MX; sending services from SPF; SPF, DMARC, DKIM, MTA-STS and BIMI; inbound gateways (Cisco, Cloudflare, Sophos, Mailgun); an A–F email security grade
- **WHOIS / RDAP registration**: registrar, created, updated and expiry dates, domain age, days until expiry, registry status
- **DNS lookup and hosting**: A, AAAA, MX, NS, TXT, CAA and `www` CNAME records, DNS provider, IP, ASN, network owner and country
- **SSL certificate and security headers**: issuer, validity dates, days left, protocol, validity; HSTS, CSP, X-Frame-Options, Referrer-Policy, Permissions-Policy
- **Optional add-ons**: a deep scan of up to 4 linked pages, and contact emails, phones and social profiles published on the site

#### Why run it on Apify?

- **Call it as an API** from any language, or let **AI agents** use it through MCP.
- **Schedule it** and get **only what changed**: new technologies, new SaaS, a new email provider, an expiring domain or certificate.
- **Connect it** to Google Sheets, Zapier, Make, n8n or a webhook, or download any run as CSV or Excel.

***

### Why use this BuiltWith and Wappalyzer alternative?

**One row instead of four tools.** Tech stack, DNS-verified SaaS, email security, WHOIS, DNS and SSL arrive together, so you don't have to join the output of a tech detector, a WHOIS tool, a DNS tool and an SSL checker.

**Evidence, not guesses.** Every technology comes with a confidence score and the exact header, script, DNS record or HTML snippet that proved it, so you can check any detection yourself.

**You only pay for real results.**

- A domain that doesn't exist, or where every lookup failed, is delivered **free** with the reason, which is handy for cleaning lists.
- Invalid input and duplicates aren't charged.
- Domains removed by your technology filter cost $0.001 instead of $0.003; unchanged domains in monitoring runs cost $0.0005.

**Built for automation and AI agents.** Every row always has every field (`null` or `[]` when unknown), so your code never breaks on a missing key. Input written for other tech stack and WHOIS Actors works unchanged, and every run ends with a plain-English status message.

#### How it compares

| Actor | What one run covers | Price per 1,000 domains |
|---|---|---:|
| **This Actor** | Tech stack with evidence, DNS-verified SaaS, email security, WHOIS, DNS, SSL, change monitoring | **$3** |
| [Tech Stack Detector & WHOIS, SSL Checker](https://apify.com/fguiraud/website-tech-dns-whois-ssl) | Tech stack, DNS SaaS, WHOIS, DNS, SSL, SEO and performance checks, change monitoring | $4 |
| [BuiltWith official](https://apify.com/builtwith/builtwith-official-technology-scraper) | Tech stack only | $2 |
| [Wappalyzer Alternative (nexgendata)](https://apify.com/nexgendata/wappalyzer-replacement) | Tech stack only (251 technologies) | $100 |
| [Domain WHOIS & DNS Lookup](https://apify.com/santamaria-automations/domain-whois-dns) | WHOIS and DNS only | $3 |

*Prices are the base per-domain prices from each Actor's public Store page on 5 October 2026 and may have changed since. BuiltWith also sells product, geography and marketing datasets this Actor doesn't cover.*

***

### How to do a tech stack lookup and WHOIS lookup

1. Click **Try for free** and sign in to Apify (the free plan is enough).
2. Paste your **domains, URLs or company emails** into the list, one per line. `https://www.example.com/pricing`, `blog.example.com` and `jane@example.com` all become `example.com`.
3. Keep the sections you need switched on (tech stack, DNS and email, WHOIS, SSL), and add **deep scan** or **contacts** if you want them.
4. Click **Start**. A handful of domains takes seconds; 1,000 domains took about 10 minutes in our test.
5. Download the results from the **Output** tab as JSON, CSV or Excel, or fetch them through the **API**.
6. Optional: **schedule** the run with `onlyChanges` to get only what changed.

***

### Use cases

Copy an input into the **JSON** tab, or send it through the API.

#### Qualify a lead list by tech stack

```json
{ "domains": ["stripe.com", "notion.so", "linear.app", "shopify.com"] }
```

Use `tech_names`, `cms`, `ecommerce_platform`, `saas_verified`, `email_provider` and `domain_age_days` to segment and enrich CRM accounts in one pass.

#### Find Shopify stores in a list

```json
{ "domains": ["allbirds.com", "gymshark.com", "colourpop.com", "stripe.com"], "onlyWithTechnologies": ["Shopify"] }
```

Only domains using one of the listed technologies or categories (`"Ecommerce"` works too) are delivered. Shopify is detected from DNS (Shopify's storefront IPs and `myshopify.com` CNAMEs) even when a store blocks page requests: in our test all 10 of 10 known Shopify stores matched.

#### Audit email security

```json
{ "domains": ["stripe.com", "shopify.com", "notion.so"], "includeTechnologies": false, "includeWhois": false, "includeTls": false }
```

![Email security audit with SPF, DMARC, DKIM, MTA-STS and BIMI for each domain](https://api.apify.com/v2/key-value-stores/sVImVssQJMukOyxVQ/records/domain-tech-stack-lookup-email-security.png?signature=iCeEKgAJuoq9CatG7rkU)

Read `email_provider`, `has_spf`, `has_dmarc`, `has_dkim`, the parsed `spf` and `dmarc`, and `email_security_grade`. Gateways like Cisco or Cloudflare Email Security appear in `saas_verified`.

#### Watch domain and SSL certificate expiry

```json
{ "domains": ["example.com", "example.org"], "includeTechnologies": false, "onlyChanges": true }
```

Schedule it weekly. Sort the first run by `days_until_expiry` and `tls.days_left`; later runs only return domains whose registrar, expiry or certificate changed.

#### Detect new SaaS adoption

```json
{ "domains": ["stripe.com", "linear.app", "shopify.com"], "onlyChanges": true }
```

Read `changes.saas_added`, `changes.technologies_added` and `changes.first_seen`. A company that just verified Salesforce, HubSpot or Zoom in DNS is a buying signal.

***

### Output example

One row per domain. This is a real row for stripe.com from a platform run on 4 October 2026, trimmed to the main fields (the full row has all 63 fields):

```json
{
  "domain": "stripe.com",
  "input": "stripe.com",
  "url": "https://stripe.com",
  "final_url": "https://stripe.com",
  "exists": true,
  "homepage_status": "ok",
  "status_code": 200,
  "company_name": "Stripe",
  "technologies": [
    {"name": "Atlassian", "categories": ["Development", "SaaS"], "version": null, "confidence": 100, "evidence": "dns:txt=atlassian-domain-verification=upLp21qQgja1aHG2gnAb1AmXRqb/zG0UK1a0n3zTSXZg5DgOSttR3i5uzA3T9Cdk", "source": "dns"},
    {"name": "HSTS", "categories": ["Security"], "version": null, "confidence": 100, "evidence": "headers:strict-transport-security=max-age=63072000; includeSubDomains; preload", "source": "headers"},
    {"name": "Nginx", "categories": ["Web servers", "Reverse proxies"], "version": null, "confidence": 100, "evidence": "headers:server=nginx", "source": "headers"}
  ],
  "tech_count": 25,
  "tech_names": ["Amazon Route 53", "Amazon Web Services", "Anthropic", "Apple", "Atlassian", "Canva", "Cursor", "Docker", "DocuSign", "ElevenLabs", "Google Search Console", "Google Workspace", "HackerOne", "HSTS", "Linear", "LiveRamp", "Meta", "Microsoft 365", "Nginx", "Open Graph", "OpenAI", "Postman", "Priority Hints", "Salesforce", "Stripe"],
  "hosting_provider": "Amazon Web Services",
  "web_server": "Nginx",
  "payment_providers": ["Stripe"],
  "saas_verified": [
    {"name": "Microsoft 365", "record": "TXT", "evidence": "TXT: MS=ms80697640"},
    {"name": "Meta", "record": "TXT", "evidence": "TXT: facebook-domain-verification=m7id9rt8ehlgcg9tt2yggbsi6gro7i"}
  ],
  "email_provider": "Google Workspace",
  "has_spf": true,
  "has_dmarc": true,
  "has_dkim": true,
  "dmarc": {"record": "v=DMARC1; p=reject; pct=100; fo=1; rua=mailto:dmarc-reports@stripe.com; ruf=mailto:dmarc-forensics@stripe.com;", "policy": "reject", "pct": 100, "rua_provider": "stripe.com"},
  "email_security_grade": "A",
  "dns_provider": "Amazon Route 53",
  "ip": "198.202.176.161",
  "asn": "16509",
  "as_org": "AMAZON-02 - Amazon.com, Inc., US",
  "registrar": "SafeNames Ltd.",
  "created_date": "1995-09-12T04:00:00Z",
  "expiry_date": "2027-09-11T04:00:00Z",
  "domain_age_days": 11345,
  "days_until_expiry": 341,
  "whois_source": "rdap",
  "tls": {"issuer": "CN=DigiCert G5 TLS ECC SHA384 2021 CA1,O=DigiCert\\, Inc.,C=US", "valid_to": "2026-12-10T23:59:59+00:00", "days_left": 67, "protocol": "TLSv1.3", "valid": true},
  "errors": {}
}
```

`technologies` lists all 25 detections (3 shown) and `saas_verified` all 10 DNS-verified tools (2 shown). Source: run `AuOwVSJ5aOzWNGoFC`. A DNS verification token shows the company set up the service at some point; it doesn't prove a current paid subscription.

#### All fields

- **Identity:** `domain`, `input`, `url`, `final_url`, `redirects_to_other_domain`, `exists`
- **Homepage:** `homepage_status` (`ok`, `blocked`, `error`, `no_website`, `parked`), `status_code`, `title`, `meta_description`, `language`, `company_name`, `logo_url`, `generator`
- **Technologies:** `technologies[]` with `name`, `categories`, `version`, `confidence`, `evidence`, `source`; shortcuts `cms`, `ecommerce_platform`, `analytics`, `tag_managers`, `frameworks`, `cdn`, `hosting_provider`, `web_server`, `payment_providers`, `marketing_automation`, `live_chat`, `tech_count`, `tech_names`
- **SaaS and email:** `saas_verified[]`, `email_provider`, `email_senders`, `has_spf`, `has_dmarc`, `has_dkim`, `spf`, `dmarc`, `has_mta_sts`, `has_bimi`, `email_security_grade`
- **DNS and hosting:** `dns` (`a`, `aaaa`, `mx`, `ns`, `txt`, `caa`, `www_cname`), `dns_provider`, `ip`, `asn`, `as_org`, `ip_country`
- **WHOIS:** `registrar`, `created_date`, `expiry_date`, `updated_date`, `domain_age_days`, `days_until_expiry`, `registry_status`, `registrant_org`, `registrant_country`, `whois_source`
- **SSL and headers:** `tls`, `security_headers`
- **Add-ons:** `emails`, `phones`, `socials`
- **Monitoring:** `changes`
- **Meta:** `scraped_at`, `errors` (which lookups failed or were cut short, and why)

In the **Output** tab you can switch between **Overview**, **Technologies** (one row per technology), **Email security & SaaS**, **DNS & hosting**, **WHOIS & SSL**, **Changes** and a flat **CSV** view that opens cleanly in spreadsheets.

#### How complete is the data?

From a 1,000-domain test run (popular sites plus a mix of SMB, Shopify and non-.com domains, 4 October 2026):

| Section | Result |
|---|---|
| Homepage read | 749 ok, 182 blocked by bot protection, 69 other (no website, errors, non-HTML) |
| At least one technology | 990 / 1,000 |
| At least one SaaS tool verified in DNS | 885 / 1,000 |
| Registration data | 848 RDAP, 56 port-43 WHOIS, 86 limited by the registry, 10 unavailable |
| Email provider identified | 655 / 1,000 (others use gateways, self-hosted or unlisted mail servers) |
| SSL certificate read | 969 / 1,000 |

***

### How much does it cost?

You pay per domain, with no subscription and no proxy fees.

| You get | Price |
|---|---|
| Each run | $0.002 |
| Each domain profile (tech stack + DNS + email + WHOIS + SSL) | **$0.003** ($3 per 1,000) |
| + deep scan | $0.002 per domain where at least one extra page was fetched |
| + contacts | $0.001 per domain where a contact or social profile was found |
| Domain removed by your technology filter | $0.001 |
| Unchanged domain in a monitoring run | $0.0005 |
| Domain that doesn't exist, or where every lookup failed | free |

On paid Apify plans the domain price drops to **$2.70** (Bronze), **$2.55** (Silver) or **$2.40** (Gold) per 1,000.

**What typical jobs cost (free-plan prices):**

| Job | Cost |
|---|---:|
| 100 domains | $0.302 |
| 1,000 domains | $3.002 |
| 100 domains with deep scan on every one | $0.502 |
| Screen 1,000 domains for Shopify, 200 match | $1.402 |
| Weekly monitoring of 1,000 domains, 20 changed | $0.552 per run |

#### Is it free?

Apify's free plan includes $5 of credit every month, which covers about 1,600 domains. Your maximum charge per run is a hard cap: the Actor stops cleanly when it's reached and charges only for rows delivered.

***

### API and AI agents

One HTTP request runs the domain lookup and returns the rows as JSON. Use your Apify API token (Console → Settings → API & Integrations):

```bash
curl -X POST "https://api.apify.com/v2/acts/devarq~domain-tech-stack-whois-dns/run-sync-get-dataset-items?token=YOUR_APIFY_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"domains": ["stripe.com", "shopify.com", "notion.so"]}'
```

JavaScript (`npm install apify-client`):

```javascript
import { ApifyClient } from 'apify-client';

const client = new ApifyClient({ token: 'YOUR_APIFY_TOKEN' });
const run = await client.actor('devarq/domain-tech-stack-whois-dns').call({ domains: ['stripe.com', 'shopify.com'] });
const { items } = await client.dataset(run.defaultDatasetId).listItems();
```

Python (`pip install apify-client`):

```python
from apify_client import ApifyClient

client = ApifyClient("YOUR_APIFY_TOKEN")
run = client.actor("devarq/domain-tech-stack-whois-dns").call(run_input={"domains": ["stripe.com", "shopify.com"]})
profiles = client.dataset(run.default_dataset_id).list_items().items
```

`run-sync-get-dataset-items` waits up to 5 minutes, which is enough for a few hundred domains. For bigger lists, start the run asynchronously and read the dataset when it finishes.

#### Use with AI agents (MCP)

Add this Actor to Claude, ChatGPT, Cursor or any MCP client through the Apify MCP server, then ask:

- "What is stripe.com built on?"
- "Which of these 200 domains use Shopify? Return only those."
- "Check the email security of these 20 company domains and list any without DMARC."
- "Which of these domains or SSL certificates expire in the next 60 days?"

Agents don't need perfect input. `{"domain": "stripe.com"}`, `{"urls": "stripe.com, shopify.com"}`, a pasted list of URLs or a company email all work. If nothing usable is in the input, the run says so plainly and charges no results.

***

### Monitoring: get only what changed

Set `"onlyChanges": true` and schedule the run (daily or weekly) with the same domains:

- The first run returns every domain and saves a snapshot.
- Later runs return only domains whose technologies, verified SaaS, email provider, DNS provider, registrar, expiry date or certificate changed. Each row's `changes` field says what changed (`technologies_added`, `saas_added`, `expiry_changed: {from, to}`…), and `first_seen` dates when each technology appeared.
- Unchanged domains aren't returned and cost $0.0005 each.
- If a lookup fails during a run (for example a slow WHOIS server), that part is treated as unchanged, so you're never alerted or charged for a change that didn't happen.
- You can add domains to the list at any time; the existing ones keep their history.

***

### Detection accuracy

- **Precision:** every detection with confidence 50 or more was checked by hand on saved homepages. On 32 held-out domains, **268 of 268** were correct (the 30 domains used to tune the rules: 244 of 244).
- **Against BuiltWith** on 10 core labels (Shopify, WordPress, WooCommerce, Webflow, Next.js, Vercel, HubSpot CMS Hub, Squarespace, Wix, Drupal) for 10 domains: **92.3% precision and 92.3% recall**. The one "false positive" is Webflow on teachable.com, which has direct Webflow markup that BuiltWith's profile missed.

These are checks on dated pages, not a recall claim across all 7,600+ known technologies. Raise `minConfidence` for stricter output.

***

### FAQ

#### Is it legal to look up tech stacks and WHOIS data?

This Actor reads only public information: a site's public homepage (like any browser), public DNS records, public RDAP/WHOIS registry data and the site's SSL certificate. It doesn't log in, bypass bot protection or collect personal data. WHOIS output is limited to the registrant **organisation and country**, never names, emails or phone numbers. The contacts add-on returns only details a company published on its own site. You're responsible for how you use the data, including any rules on contacting people; if you're unsure, check with a lawyer.

#### Where does the data come from?

The target site's homepage, DNS over HTTPS (Cloudflare and Google), RDAP and port-43 WHOIS registries, a TLS handshake for the certificate, and Team Cymru for IP-to-network data. No third-party scraping. Technology fingerprints come from pinned snapshots of [enthec/webappanalyzer](https://github.com/enthec/webappanalyzer) and [HTTP Archive's Wappalyzer data](https://github.com/HTTPArchive/wappalyzer) (GPL-3.0, credited and kept unmodified), plus our own DNS rules, each confirmed on at least three live domains.

#### What are the limits?

- **Bot protection:** about 18% of homepages in our 1,000-domain test blocked automated requests (`homepage_status: blocked`). Those rows still get DNS, SaaS, email, WHOIS, SSL and header-based technologies, but not technologies visible only in the page. Shopify stores often block page requests: Shopify itself is still detected from DNS, but page-only tools like Klaviyo usually aren't.
- **JavaScript-only technologies:** the Actor reads the HTML the server sends, without a browser, so tools injected only by JavaScript may be missed. `deepScan` checks up to 4 more pages.
- **WHOIS policies:** some registries (.de, .eu, .ch, .jp and others) publish no dates; `whois_source` is then `limited`.
- **Subdomains** are looked up as their registrable domain (`blog.example.co.uk` → `example.co.uk`), except hosted sites like `name.github.io`.

#### How many domains can one run handle?

With the default 4 GB of memory, 1,000 domains took about 10 minutes, so the default 1-hour timeout fits about 5,000 domains. For bigger lists, raise the timeout in **Run options** (allow about 11 minutes per 1,000 domains) or split the list. Rows are saved in batches of 50, so a run that hits its timeout keeps, and charges for, only what it delivered. One input accepts up to 100,000 unique domains.

#### I'm switching from another tech stack or WHOIS Actor. Do I need to change my input?

No. Input written for BuiltWith (`startDomains`), Wappalyzer-style Actors (`urls`, `startUrls`, `websites`, `url`, `timeout_seconds`) and WHOIS/DNS Actors (`domains`, `domain`, `includeWhois`, `includeDNS`) works unchanged; just change the Actor ID. Common output names like `url`, `final_url`, `status_code`, `technologies`, `tech_count`, `tech_names`, `registrar`, `has_spf` and `has_dmarc` are the same.

#### Why is `hosting_provider` empty for some domains?

It names where the website itself runs: from the site's own response headers (Vercel, Netlify, WP Engine...) or the network that owns its IP address (Amazon Web Services, Google Cloud...). When the site sits behind a CDN such as Cloudflare, Fastly or Akamai, the real host is hidden, so the field is empty and the CDN appears in `cdn`. DNS servers and email-sending services are deliberately not counted as hosting.

#### Why is `email_provider` empty for some domains?

The MX record points to an email security gateway (listed in `saas_verified`), a self-hosted mail server, or a provider not in our list. `dns.mx` always has the raw records.

#### How is the email security grade calculated?

- **A:** SPF and DMARC exist, DMARC is `reject` or `quarantine`, and SPF ends in `-all` or `~all`
- **B:** SPF and DMARC exist but don't meet every A condition
- **C:** SPF only
- **D:** DMARC only
- **F:** neither

`has_dkim` is `true` when a key is found on a common selector (`google`, `selector1`, `selector2`, `k1`, `s1`, `default`) and `null` otherwise, because not finding one doesn't prove DKIM is off.

#### My run returned no rows. Why?

The status message always says why: no valid domains in the input (nothing is charged), your technology filter matched nothing, or, in monitoring mode, nothing changed since the last run. If DNS lookups are unreachable or most domains fail every lookup, the run fails clearly instead of returning bad data.

#### Is this affiliated with BuiltWith or Wappalyzer?

No. It's an independent tool, **not affiliated with or endorsed by BuiltWith or Wappalyzer**. Their names are used only to describe compatibility.

#### Found a bug or need a field?

Open an issue on this page or email support@devarq.dev.

***

### Input reference

| Field | Type | Default | Description |
|---|---|---|---|
| `domains` | array | prefilled with 3 examples | Domains, URLs or company emails |
| `includeTechnologies` | boolean | `true` | Tech stack from the homepage (plus DNS-based technologies) |
| `includeDns` | boolean | `true` | DNS records, email provider and security, SaaS verified in DNS, IP and hosting |
| `includeWhois` | boolean | `true` | RDAP with port-43 WHOIS fallback |
| `includeTls` | boolean | `true` | SSL certificate |
| `deepScan` | boolean | `false` | Up to 4 linked pricing/contact/careers/product pages (+$0.002) |
| `includeContacts` | boolean | `false` | Emails, phones and social profiles published on the site (+$0.001) |
| `onlyWithTechnologies` | array | `[]` | Keep domains using any of these technologies or categories |
| `minConfidence` | integer | `50` | Drop detections below this confidence (0–100) |
| `maxItems` | integer | `1000` | Maximum rows; `0` = no limit (your maximum charge still applies) |
| `timeoutSeconds` | integer | `30` | Network time per domain (5–60 seconds); whatever arrived in time is still analysed |
| `onlyChanges` | boolean | `false` | Return only domains that changed since the last run |

***

### Changelog

**0.1** (October 2026): first release. Tech stack, DNS-verified SaaS, email security, WHOIS/RDAP, DNS, hosting and SSL in one row per domain; deep scan and contacts add-ons; technology filter; change-only monitoring; seven output views.

# Actor input Schema

## `domains` (type: `array`):

Domains to look up, one per item, e.g. \["stripe.com", "https://www.shopify.com/pricing", "jane@notion.so"]. URLs, subdomains and emails are reduced to the registrable domain (blog.example.co.uk → example.co.uk); duplicates are removed and charged once. Free-mail addresses (gmail.com, outlook.com…) are skipped. $0.003 per delivered domain; domains that don't exist are delivered free with exists: false.

## `includeTechnologies` (type: `boolean`):

Fetch the homepage and detect technologies: CMS, ecommerce platform, frameworks, analytics, tag managers, CDN, hosting, payments, marketing and chat tools, with version, confidence and evidence. Default: on. Included in the $0.003 domain price.

## `includeDns` (type: `boolean`):

DNS records (A, AAAA, MX, NS, TXT, CAA, www CNAME), DNS provider, IP/ASN hosting, email provider, SPF, DMARC, DKIM, MTA-STS, BIMI, an A–F email security grade, and SaaS tools the company verified in DNS (e.g. Salesforce, Microsoft 365, Atlassian). Default: on. Included in the domain price.

## `includeWhois` (type: `boolean`):

Registrar, created, updated and expiry dates, domain age, days until expiry and registry status, via RDAP with port-43 WHOIS fallback. Only the registrant organisation and country are returned, never personal data. Default: on. Included in the domain price.

## `includeTls` (type: `boolean`):

Certificate issuer, valid from/to, days left, SAN count, TLS protocol and validity (expired or mismatched certificates are reported, not skipped). Default: on. Included in the domain price.

## `deepScan` (type: `boolean`):

Also scan up to 4 linked pages on the same site (pricing, contact, careers, product/checkout) to find more technologies. Adds $0.002 per domain, charged only when at least one extra page was fetched. Default: off.

## `includeContacts` (type: `boolean`):

Collect emails, phone numbers and social profile links (LinkedIn, X, Facebook, Instagram, YouTube, GitHub, TikTok) published on the homepage and contact page. Never guesses emails. Adds $0.001 per domain, charged only when something was found. Default: off.

## `onlyWithTechnologies` (type: `array`):

Keep only domains that use any of these technology names or categories (case-insensitive), e.g. \["Shopify", "Klaviyo"] or \["Ecommerce"]. Other domains are not delivered and cost $0.001 each instead of $0.003. Default: empty (keep all).

## `minConfidence` (type: `integer`):

Drop technology detections scored below this value (0–100). Header, cookie and DNS evidence score 100; script URLs and meta tags 90; HTML, inline scripts and DOM 80; implied technologies 60. Default: 50.

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

Stop after this many delivered rows, e.g. 100. 0 = no limit (your run's maximum charge still applies). Default: 1000.

## `timeoutSeconds` (type: `integer`):

Maximum time spent fetching one domain's homepage, DNS, WHOIS and certificate (5–60). Whatever arrived in time is still analysed and delivered; slow parts are noted in errors. Deep scans allow 60 s. Default: 30.

## `onlyChanges` (type: `boolean`):

For scheduled runs: deliver only domains whose technologies, verified SaaS, email or DNS provider, registrar, expiry date or certificate changed since the last run, with a changes field listing what changed. Unchanged domains cost $0.0005 each instead of $0.003. The first run delivers everything. Default: off.

## Actor input object example

```json
{
  "domains": [
    "stripe.com",
    "shopify.com",
    "notion.so"
  ],
  "includeTechnologies": true,
  "includeDns": true,
  "includeWhois": true,
  "includeTls": true,
  "deepScan": false,
  "includeContacts": false,
  "onlyWithTechnologies": [],
  "minConfidence": 50,
  "maxItems": 1000,
  "timeoutSeconds": 30,
  "onlyChanges": false
}
```

# Actor output Schema

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

Every delivered stable-shape profile, including partial and free failed rows.

## `overview` (type: `string`):

Company, primary stack, email, hosting, domain age, and security grade.

## `technologies` (type: `string`):

One row per detected technology with confidence and evidence.

## `saasEmail` (type: `string`):

Email provider, A–F grade, SPF, DMARC, DKIM, senders and SaaS verified in DNS.

## `dns` (type: `string`):

DNS provider, A/MX/NS records, www CNAME, IP, ASN, CDN and hosting.

## `registrationTls` (type: `string`):

Registrar, registration and expiry dates, domain age, and the SSL/TLS certificate.

## `changes` (type: `string`):

Technology, SaaS, provider, expiry, and TLS changes for monitoring runs.

## `csv` (type: `string`):

Spreadsheet-friendly scalar fields with domain first.

# 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 = {
    "domains": [
        "stripe.com",
        "shopify.com",
        "notion.so"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("devarq/domain-tech-stack-whois-dns").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 = { "domains": [
        "stripe.com",
        "shopify.com",
        "notion.so",
    ] }

# Run the Actor and wait for it to finish
run = client.actor("devarq/domain-tech-stack-whois-dns").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 '{
  "domains": [
    "stripe.com",
    "shopify.com",
    "notion.so"
  ]
}' |
apify call devarq/domain-tech-stack-whois-dns --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,devarq/domain-tech-stack-whois-dns"
        }
    }
}
```

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/bdQLpadXM0XEqrexV/builds/rcc1QTqbByWeDd9OM/openapi.json
