# Tech Stack Detector: Website Technology & SaaS Lookup (`echolab/tech-stack-detector`) Actor

Bulk domains tech stack lookup: BuiltWith alternative and Wappalyzer alternative. Detect CMS, ecommerce platform, analytics, CDN, email provider and SaaS tools from public DNS plus homepage technology fingerprints.

- **URL**: https://apify.com/echolab/tech-stack-detector.md
- **Developed by:** [Echo Lab](https://apify.com/echolab) (community)
- **Categories:** Lead generation, Developer tools, SEO tools
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.50 / 1,000 domains

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

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

## Website Tech Stack Detector — Technology Lookup & Public DNS SaaS Discovery

### What it does

A bulk tech stack detector and technology lookup for public websites. This BuiltWith alternative and Wappalyzer alternative combines homepage fingerprints with public DNS to help answer **what CMS is this site using**, discover email infrastructure, and identify SaaS verification signals invisible on the homepage.

- 206 independently authored technology fingerprints; no licensed Wappalyzer or BuiltWith database.
- Homepage HTML, script/link URLs, response headers, cookie **names**, and meta generator.
- Public MX, TXT/SPF, NS and CNAME records, with Cloudflare DNS-over-HTTPS and Google fallback.
- Evidence and confidence per detection, CSV-friendly names and category groups.
- Robots.txt respected by default, bounded body size and concurrency; no browser required.

#### Detected categories

| Categories | Examples |
|---|---|
| CMS / Ecommerce / Website builder | WordPress, Drupal, Shopify, WooCommerce, Wix, Webflow |
| JavaScript framework / Web framework / JS library / UI framework | Next.js, Nuxt, Express, ASP.NET, jQuery, Bootstrap |
| Analytics / Tag manager / Advertising/pixels / A/B testing | Plausible, Google Tag Manager, Meta Pixel, Optimizely |
| Marketing automation / CRM | HubSpot, Klaviyo; verification signals complement visible CRM integrations |
| Email delivery / Email hosting | SendGrid, Mailgun, Amazon SES, Google Workspace, Microsoft 365 |
| Live chat/support / Payments | Intercom, Zendesk, Stripe, PayPal |
| CDN / Hosting/PaaS / DNS provider / Web server / Security/WAF | Cloudflare, Vercel, Route 53, nginx |
| Consent/cookie banner / Fonts / Video / Search | OneTrust, Google Fonts, Vimeo, Algolia |
| Reviews / Forms / Scheduling | Trustpilot, Typeform, Calendly |
| Domain verification (SaaS used) | Atlassian, OpenAI, Zoom, Adobe, Slack |

### Use cases

- Lead qualification and sales prospecting lists: find websites using Shopify / HubSpot within your supplied domain list.
- Competitor research and agency technology audits.
- Market share studies across your own representative domain samples.
- Enriching CRM with email provider lookup and SaaS infrastructure hints.

### Input

| Field | Default | Description |
|---|---|---|
| domains | wordpress.org, stripe.com, shopify.com | Array of domains or URLs; normalized and deduplicated. Invalid lines skipped, not billed. |
| checkHomepage | true | HTTPS homepage GET, at most 2 MB, up to five redirects; HTTP fallback on connection/TLS failure. |
| respectRobotsTxt | true | Skip homepage if root is disallowed for our UA or wildcard. DNS checks continue. |
| checkDns | true | Public MX, TXT, NS and CNAME lookup. |
| categories | \[] | Optional category allowlist; empty returns all. |
| maxConcurrency | 5 | Domain workers, 1–20. |
| timeoutSecs | 20 | Per-request timeout, 1–60 seconds. |

```json
{"domains":["shopify.com","https://wordpress.org/","stripe.com"],"checkDns":true,"checkHomepage":true,"maxConcurrency":5}
```

### Output

One item per processed, valid, unique domain; failed checks still produce a billed row.

```json
{"domain":"example.com","inputValue":"https://example.com/","finalUrl":"https://example.com/","httpStatus":200,"title":"Example store","technologies":[{"name":"Shopify","category":"Ecommerce","version":null,"confidence":"high","evidence":"scriptSrc: cdn.shopify.com/","website":"https://shopify.com"}],"technologyNames":["Shopify"],"categories":{"Ecommerce":["Shopify"]},"emailProvider":null,"dnsProvider":null,"hosting":null,"cdn":null,"homepageSkipped":null,"error":null,"errorMessage":null,"checkedAt":"2026-11-08T00:00:00+00:00"}
```

| Field | Description |
|---|---|
| domain / inputValue | Normalized hostname and first supplied value. |
| finalUrl / httpStatus / title | Final homepage URL, status, and trimmed title; null when not fetched. |
| technologies | Name, category, version (if captured), high/medium confidence, short evidence and vendor website. |
| technologyNames / categories | Flat names for CSV filtering and category-to-names mapping. |
| emailProvider / dnsProvider / hosting / cdn | Best guesses from all detections, including when categories are filtered. MX gateways may hide the underlying mailbox provider. |
| homepageSkipped | null, robots_txt, or fetch_failed. |
| error / errorMessage | Error when enabled checks cannot complete; domain_not_found identifies NXDOMAIN, timeout identifies the wall-clock cap, and internal_error isolates unexpected errors. DNS-only detections survive homepage failures. |
| checkedAt | UTC timestamp. |

### Pricing

You pay only for domains saved to the dataset, plus a tiny per-run start fee; Apify platform usage is included in the price. Duplicate domains and truly invalid input lines are not saved or billed. A valid domain with failed network checks still has a saved result and is billed. Processing stops normally when the dataset event-charge limit is reached. The current price per 1,000 domains is shown on the Pricing tab of this page.

### Tips / limits

Detection means fingerprints, not a comprehensive inventory or proof of a paid subscription. Verification records may be stale or represent a free service; SPF indicates authorized senders, not necessarily current use. Generic verification tokens do not establish a specific Google or Microsoft product. Homepage-only analysis does not execute JavaScript and may miss technologies loaded after interaction. Vendor CDN URLs can identify embedded integrations rather than the site's primary platform. Subdomains use their own DNS records; submit the company apex for email provider lookup. DNS CNAME flattening can hide hosting hints. HTTP errors, robots restrictions and anti-bot pages reduce recall. No CAPTCHA solving or anti-bot bypass. Rate limits and transient errors retry up to three total attempts with backoff and Retry-After (capped at 30 seconds). Each domain has a 120-second wall-clock cap.

### Compliance & data source

Only public homepages, robots.txt and official public DNS-over-HTTPS endpoints are accessed, with User-Agent `EchoLab-Apify-Actor/tech-stack-detector (+https://apify.com/echolab)`. No login, personal contact extraction, cookie values or raw verification tokens are output. Titles redact email addresses and phone-like strings; do not submit credential-bearing URLs or URLs containing personal data. Users are responsible for complying with each source's terms and applicable laws.

### Support

Open an issue on the Actor's Issues tab.

More real output, worked pricing examples and a comparison with alternatives: https://echolab-tools.pages.dev/tech-stack-detector/

# Actor input Schema

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

Domains or HTTP(S) URLs; normalized and deduplicated. Invalid lines are skipped.

## `checkHomepage` (type: `boolean`):

Fetch homepage without JavaScript execution.

## `respectRobotsTxt` (type: `boolean`):

Skip homepage if robots.txt forbids root; DNS still runs.

## `checkDns` (type: `boolean`):

Read MX, TXT, NS and CNAME records over HTTPS.

## `categories` (type: `array`):

Optional category allowlist. Empty means all.

## `maxConcurrency` (type: `integer`):

Concurrent domain workers (1–20).

## `timeoutSecs` (type: `integer`):

Per-request timeout in seconds (1–60).

## Actor input object example

```json
{
  "domains": [
    "wordpress.org",
    "stripe.com",
    "shopify.com"
  ],
  "checkHomepage": true,
  "respectRobotsTxt": true,
  "checkDns": true,
  "categories": [],
  "maxConcurrency": 5,
  "timeoutSecs": 20
}
```

# Actor output Schema

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

One item per processed domain.

# 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": [
        "wordpress.org",
        "stripe.com",
        "shopify.com"
    ],
    "checkHomepage": true,
    "respectRobotsTxt": true,
    "checkDns": true,
    "categories": [],
    "maxConcurrency": 5,
    "timeoutSecs": 20
};

// Run the Actor and wait for it to finish
const run = await client.actor("echolab/tech-stack-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 = {
    "domains": [
        "wordpress.org",
        "stripe.com",
        "shopify.com",
    ],
    "checkHomepage": True,
    "respectRobotsTxt": True,
    "checkDns": True,
    "categories": [],
    "maxConcurrency": 5,
    "timeoutSecs": 20,
}

# Run the Actor and wait for it to finish
run = client.actor("echolab/tech-stack-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 '{
  "domains": [
    "wordpress.org",
    "stripe.com",
    "shopify.com"
  ],
  "checkHomepage": true,
  "respectRobotsTxt": true,
  "checkDns": true,
  "categories": [],
  "maxConcurrency": 5,
  "timeoutSecs": 20
}' |
apify call echolab/tech-stack-detector --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,echolab/tech-stack-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/GwQcwu7TPrQvDTueT/builds/4V0GbLIRnHnsFnRZm/openapi.json
