Evolc Signals API & MCP

Company signals in your code and your AI assistant.

The same data as Signals: European companies that just started hiring for a function, opened a leadership role, raised money or turned profitable, with evidence for every signal. Ask Claude “which Czech and Slovak companies just started hiring SDRs?” or pull the list into your CRM. Company facts only, never personal data.

Sign in to get an API key

Plans and quotas

Without an accountFree accountWork e-mailScout or Pipeline
API & MCP calls——200 calls / month10,000 calls / month
Companies per search——First 100All, paged
Accounts per account check——1,0005,000
Revenue, growth and all evidence——✓✓

Verify your work e-mail: 14 days of full Signals free: the first account from each company gets 1,000 calls a month and every result for 14 days, no card needed. Quotas count every data request that returns results (REST call or MCP tool call; empty pages, unknown companies and our errors are free) per account per calendar month (UTC), across all of its keys (up to 5). Each key also allows 60 requests per minute. Results are gated exactly like the Signals page: total is always exact, and companies beyond your plan are counted in locked.

Authentication

Create a key on your API keys page. It starts with evk_ and is shown once; we store only a hash. Send it as a bearer token. Keys stop working when revoked, or when the account no longer has a verified work e-mail or a paid plan. The API is for servers: there are no CORS headers, so never put a key in browser code.

curl -s https://companies.evolc.com/api/v1/signals?countries=SK,CZ&families=sales&subs=sdr_bdr \
  -H "Authorization: Bearer evk_…"

GET /api/v1/signals

Companies with signals, strongest first. Lists are comma-separated; values in one list are OR, different filters are AND. Unknown parameters or values are a 400, never silently ignored.

ParameterValues
countriesISO-2 codes, e.g. SK,CZ,PL,HU,AT,DE (up to 12)
industriesIndustry keys, e.g. software_saas,fintech
familiesJob functions: engineering, data, product, design, sales, marketing, customer, operations, finance, people, legal, executive, robotics, manufacturing
subsSub-roles of those functions, e.g. sdr_bdr, account_executive, customer_success, product_marketing
kindshiring, first_in_function, hiring_spike, leadership_role_open, funding, revenue_jump, profitability_flip, director_change, news
days7, 30, 90 (default 30)
qName, website or one-liner contains (≤ 100 characters)
sinceOnly signals newer than this ISO date, e.g. 2026-10-01
exclude_volume1 (default) leaves out volume hirers: staffing agencies, branch and field-sales networks, brokers, fundraisers. 0 includes them, marked "volume_hiring": true and ranked lower.
limit, offset1–100 (default 25); offset ≤ 10 000. Use next for the next page.
{
  "items": [{
    "id": "…", "name": "Acme s.r.o.", "domain": "acme.sk", "website": "https://acme.sk", "slug": "acme",
    "country": "SK", "city": "Bratislava", "industry": "software_saas", "business_model": "b2b_saas",
    "employee_band": "20-49", "founded_year": 2015, "one_liner": "…", "open_jobs": 4, "hot_score": 50,
    "latest_revenue": 1250000, "revenue_growth": 0.42,
    "hiring": [{ "family": "sales", "sub": "sdr_bdr", "open": 3, "new": 2 }],
    "signals": [{ "kind": "hiring", "title": "SDR", "url": "https://acme.sk/jobs/sdr", "at": "2026-10-25T00:00:00Z" }],
    "strength": 80, "last_signal_at": "2026-10-25T00:00:00Z",
    "more_signals": 0, "financials_locked": false, "evolc_url": "https://companies.evolc.com/company/acme"
  }],
  "total": 240, "locked": 140, "next": 25, "window_days": 30,
  "meta": { "tier": "work", "limit_remaining": 187, "quota": 200, "upgrade": "…" }
}

GET /api/v1/companies/:slug and ?domain=

The public company profile, as on its Evolc page: description, industry, size, founded year, open jobs, highlights with evidence, filed financials (newest first) and sources. Leadership and other people are not included.

curl -s https://companies.evolc.com/api/v1/companies/acme -H "Authorization: Bearer evk_…"
curl -s "https://companies.evolc.com/api/v1/companies?domain=acme.sk" -H "Authorization: Bearer evk_…"

GET /api/v1/searches

Your saved Signals searches with their filters (query uses the same names as /api/v1/signals). Free of quota, like key and MCP handshakes.

POST /api/v1/accounts

Check your own account list, for example a CRM export: which of these companies are hiring, raised money or grew, and which are quiet. The same matching as Your accounts: exact by domain (a website URL or an e-mail address at the company works too), otherwise by name within a country, otherwise by a unique name; never fuzzy. Your list is used only to answer the request and is not stored.

curl -s https://companies.evolc.com/api/v1/accounts   -H "Authorization: Bearer evk_…" -H "content-type: application/json"   -d '{"accounts":[{"domain":"acme.sk","ref":"crm-123"},{"name":"Globex","country":"CZ"}],"families":["sales"],"days":30}'
FieldMeaning
accounts1 to your plan’s limit (1,000 with a work e-mail, 5,000 on Scout and Pipeline), each {domain?, name?, country?, ref?} with a domain or a name. ref is your record id, echoed back.
families, subs, kinds, days, since, exclude_volumeAs for /api/v1/signals. Countries, industries and q don’t apply to a known list.

Answer: items in input order, each {ref, input, match: {company_id, slug, name, domain, country, confidence} | null, unmatched_reason, signals_in_window, company, locked}, plus matched, unmatched, with_signals, quiet, locked. confidence is domain, name_country or name (check those). Matched accounts are ranked (signals first by strength, then quiet ones by open roles) and the first 100 carry company on the work tier, all on paid plans; the rest are locked. Cost: one call per started 100 accounts.

Errors

Every error is JSON: {"error":{"code":"…","message":"…"}}, plus param for invalid parameters. Successful data calls return x-quota-limit and x-quota-remaining headers.

StatuscodeMeaning
400invalid_parameterUnknown parameter or value; see param. Does not use quota.
401unauthorized, invalid_keyNo bearer key, or a wrong or revoked one.
403plan_requiredThe key's account no longer has a work e-mail or paid plan.
404not_foundNo such company or endpoint.
429rate_limited, quota_exceededMore than 60 requests a minute, or the monthly quota is used up. See retry-after.
503unavailableSignals are briefly unavailable; retry.

MCP server for Claude and other AI assistants

A remote MCP server (Streamable HTTP) at https://companies.evolc.com/mcp, authenticated with OAuth (connect and sign in) or the same API key. Tools: search_signals, get_company, check_accounts, search_tenders, list_saved_searches. Each tool call counts as one API call; check_accounts takes up to 100 accounts per call.

Claude.ai, ChatGPT and other connectors (no key needed)

Add a custom connector with the URL https://companies.evolc.com/mcp, then sign in to Evolc and allow access. Claude.ai: Settings → Connectors → Add custom connector. ChatGPT: Settings → Apps & Connectors → Create. The app appears on your API keys page as a connected app, uses your plan’s quota, and is disconnected by revoking it there.

Claude Code

claude mcp add --transport http evolc https://companies.evolc.com/mcp

Run /mcp in Claude Code to sign in. Or skip OAuth and send a key:

claude mcp add --transport http evolc https://companies.evolc.com/mcp --header "Authorization: Bearer evk_…"

Claude Desktop

Add to claude_desktop_config.json (Settings → Developer → Edit config); mcp-remote bridges the remote server and sends the header.

{
  "mcpServers": {
    "evolc": {
      "command": "npx",
      "args": ["-y", "mcp-remote", "https://companies.evolc.com/mcp", "--header", "Authorization:${EVOLC_AUTH}"],
      "env": { "EVOLC_AUTH": "Bearer evk_…" }
    }
  }
}

Other clients

Any client that supports Streamable HTTP and custom headers works: POST JSON-RPC to /mcp with Authorization: Bearer evk_…. The server is stateless (no sessions, no server-sent events) and supports protocol versions 2025-11-25, 2025-06-18, 2025-03-26, 2024-11-05.

Try: “Which companies in Czechia and Slovakia started hiring SDRs in the last 30 days and also raised money?”

Into your CRM: HubSpot, Pipedrive and others

No CRM app to install. On Scout and Pipeline there are two ways, and both work with HubSpot, Pipedrive and any CRM that imports files or has a Zapier, Make or n8n integration.

1. Import a CSV

On any search, account check or watchlist, open Export for HubSpot / Pipedrive. The files use the column names each CRM maps on its own:

FormatColumns
HubSpotCompany name, Company Domain Name, City, Country/Region, Industry, Number of Employees, Description, Evolc signal, Evolc signal date, Evolc URL
PipedriveOrganization - Name, Organization - Address, Organization - Evolc signal, Organization - Evolc signal date, Organization - Evolc URL

2. Webhook → Zapier, Make or n8n → your CRM

  1. Create a webhook trigger: in Zapier Webhooks by Zapier → Catch Raw Hook (raw, so the signature can be checked), in Make a Custom webhook, in n8n a Webhook node. Copy its URL.
  2. In Signals, open a saved search or watchlist, add the URL under Delivery → Add webhook, copy the signing secret (shown once) and send a test.
  3. Check the signature in a code step (Zapier Code, n8n Code, or your own endpoint) with one of the snippets below, then loop over items (Zapier Looping, Make Iterator, n8n Split Out).
  4. For each company, search the CRM by domain (HubSpot) or by name (Pipedrive), then create the company if it is missing or update it if it exists, mapping the fields below.
Payload fieldHubSpot companyPipedrive organization
items[].nameCompany nameOrganization name
items[].domainCompany Domain Name (the match key)Website, or a custom “Domain” field to search on
items[].city, items[].countryCity, Country/RegionAddress
items[].signals[0].titleEvolc signal (custom property)Evolc signal (custom field)
items[].signals[0].atEvolc signal date (custom property)Evolc signal date (custom field)
items[].evolc_urlEvolc URL (custom property)Evolc URL (custom field)

Each company is sent once per destination. Every delivery has its own Evolc-Delivery id. Company facts only, never personal data.

The payload

POST https://hooks.example.com/your-webhook
Content-Type: application/json
Evolc-Signature: t=1793174400,v1=5f2c…
Evolc-Delivery: 7b0e…            (unique per delivery: ignore repeats)

{
  "version": 1,
  "type": "signals.digest",          // "signals.test" for the test button
  "id": "7b0e…",
  "generated_at": "2026-10-28T06:00:00.000Z",
  "search": { "id": "…", "name": "SDR hiring in CZ and SK", "kind": "search", "query": { … }, "url": "https://companies.evolc.com/signals?saved=…" },
  "items": [
    {
      "name": "Example Logistics",
      "domain": "example.com",
      "website": "https://example.com",
      "country": "CZ", "city": "Brno",
      "industry": "logistics", "employee_band": "50-99", "one_liner": "…",
      "open_jobs": 6,
      "hiring": [{ "family": "sales", "sub": "sdr_bdr", "open": 3, "new": 2 }],
      "signals": [{ "kind": "hiring", "title": "Started hiring sales: SDR/BDR", "url": "https://example.com/careers/…", "at": "2026-10-27T00:00:00Z" }],
      "latest_revenue": 4200000, "revenue_growth": 0.18,
      "strength": 82, "last_signal_at": "2026-10-27T00:00:00Z",
      "evolc_url": "https://companies.evolc.com/company/example-logistics"
    }
  ]
}

Verify Evolc-Signature in Node.js

import crypto from 'node:crypto';

// rawBody: the request body exactly as received (a string, not re-serialised JSON).
// secret: the whsec_… signing secret shown when you added the webhook.
export function verifyEvolc(rawBody, header, secret, toleranceSeconds = 300) {
  const parts = Object.fromEntries((header ?? '').split(',').map((p) => p.split('=')));
  const t = Number(parts.t);
  if (!t || Math.abs(Date.now() / 1000 - t) > toleranceSeconds) return false;
  const expected = crypto.createHmac('sha256', secret).update(`${t}.${rawBody}`).digest('hex');
  const given = Buffer.from(parts.v1 ?? '', 'hex');
  return given.length === 32 && crypto.timingSafeEqual(given, Buffer.from(expected, 'hex'));
}

Verify Evolc-Signature in Python

import hashlib, hmac, time

# raw_body: the request body exactly as received (bytes).
# secret: the whsec_… signing secret shown when you added the webhook.
def verify_evolc(raw_body: bytes, header: str, secret: str, tolerance_seconds: int = 300) -> bool:
    parts = dict(p.split("=", 1) for p in (header or "").split(",") if "=" in p)
    try:
        t = int(parts["t"])
    except (KeyError, ValueError):
        return False
    if abs(time.time() - t) > tolerance_seconds:
        return False
    expected = hmac.new(secret.encode(), f"{t}.".encode() + raw_body, hashlib.sha256).hexdigest()
    return hmac.compare_digest(expected, parts.get("v1", ""))