Threat Intelligence API & Scraper
The Threat Intelligence API returns URL, domain and IP reputation as clean JSON.
🤖 Using an AI assistant? Copy this link into ChatGPT / Claude / Cursor — it reads every endpoint and parameter instantly and tells you if this API fits your use case.
The primary url_check endpoint returns a target's type, a malicious flag, a verdict (clean, suspicious or malicious), a 0-100 score and per-feed source detail, and you can check domain and IP reputation, look up a scan and batch many targets. It is built for security, trust-and-safety and anti-abuse workflows that need a fast reputation signal without integrating each threat feed separately. One ReefAPI key, one shared credit pool, the standard envelope.
What each indicator type is actually checked against
The verdict is an aggregation of open block-list feeds, and which feeds run depends on what you passed. Every response echoes checked_sources so you can see exactly which lists were consulted for that indicator, and sources holds one block per feed that matched, each with its own weight. A feed with weight 0 is informational and does not move the verdict.
| Action and input | Feeds in checked_sources | Fields you only get here |
|---|---|---|
| url_check, a full http or https URL | urlhaus, openphish, threatfox, feodo, sslbl, spamhaus_drop, heuristics | flags[] from the heuristics pass, for example non_https and ip_literal_host |
| domain_reputation, a bare host | urlhaus, openphish, threatfox, urlscan, heuristics | malware_urls[] with status online or offline and dateadded, plus urlscan_scans |
| ip_reputation, IPv4 or IPv6 | feodo, sslbl, threatfox, urlhaus, spamhaus_drop | c2_ports[], and per-source as_name, country, first_seen and last_online |
| scan_lookup, a domain or IP | urlscan.io public search only | scans[] with uuid, server, country, tls_age_days and a per-scan malicious flag |
| batch, up to 20 mixed indicators | auto-routed per detected type | each result echoes your original string as input, plus malicious_count and ok_count |
Measured score points: 0 with no hits at all, 10 for heuristic flags alone (http://1.2.3.4/x.exe scored 10 on non_https plus ip_literal_host and the verdict stayed clean), and 80 for a single Feodo botnet-C2 hit, which flipped the verdict to malicious. dedicated_signals counts the sources that condemn the indicator itself, and it is the field to branch on rather than the raw score.
Real request and response JSON
Captured from the indexed primary action, url_check, on .
{
"method": "POST",
"url": "https://api.reefapi.com/threat-intel/v1/url_check",
"headers": {
"x-api-key": "$REEF_KEY",
"content-type": "application/json"
},
"body": {
"url": "https://github.com/"
}
}{
"ok": true,
"meta": {
"api": "threat-intel",
"endpoint": "url_check",
"mode": "live",
"latency_ms": 1285.5,
"record_count": 1,
"bytes": 7167451,
"cache_hit": false,
"method": "open_feed_aggregation_bare_dc",
"verdict": "clean",
"score": 0,
"feeds_checked": [
"urlhaus_csv",
"urlhaus_hosts",
"threatfox"
]
},
"data": {
"target": "https://github.com/",
"type": "url",
"host": "github.com",
"malicious": false,
"verdict": "clean",
"score": 0,
"dedicated_signals": 0,
"shared_hosting": true,
"sources": [
{
"source": "urlhaus",
"type": "hosts_flagged_content",
"match": "host",
"shared_hosting": true,
"dedicated": false,
"weight": 0,
"malware_urls": 56,
"active_malware_urls": 21,
"in_hostfile": false,
"note": "this is a multi-tenant host; the flagged content lives at specific paths — the domain itself is not condemned",
"sample": "https://github.com/dm-7926/dz-nvd/raw/main/udm-m.bat"
}
],
"threat_types": [
"malware_download"
],
"malware": [],
"flags": [],
"checked_sources": [
"urlhaus",
"openphish",
"threatfox"
]
}
}What the Threat Intelligence API does
| Action | Description | Concrete use case | Key params |
|---|---|---|---|
| url_check | Is a URL malicious? Checks the URLHaus malware-URL feed + OpenPhish phishing feed (exact + variants) + its host across ThreatFox/URLHaus-hosts/Feodo/SSLBL + risk flags → verdict. | Platform and DevOps teams call url_check to get is a URL malicious? Checks the URLHaus malware-URL feed + OpenPhish phishing feed (exact + va…. | url |
| domain_reputation | Domain reputation: URLHaus host listing + active malware URLs + OpenPhish phishing + ThreatFox domain IOCs + urlscan scan-history count + risk flags → consolidated verdict. | Security and supply-chain teams call domain_reputation to get domain reputation. | domain |
| ip_reputation | IP abuse signals: Feodo botnet-C2 + SSLBL botnet-C2 + ThreatFox IP IOCs + URLHaus IP-hosted malware + Spamhaus DROP hijacked-netblock → verdict + score (all keyless). | Developer-tool builders call ip_reputation to get iP abuse signals. | ip |
| scan_lookup | urlscan.io public scan history + per-scan verdict for a domain/IP (server, IP, country, TLS age, page title, malicious-flag). Open source — no key. | AI-agent developers call scan_lookup to get urlscan.io public scan history + per-scan verdict for a domain/IP (server, IP, country, TLS a…. | domain, search_field, limit |
| batch | Check up to 20 mixed indicators (URL/domain/IP, auto-routed) in one call. | Platform and DevOps teams call batch to check up to 20 mixed indicators (URL/domain/IP, auto-routed) in one call.. | targets |
Call url_check from your stack
curl -X POST https://api.reefapi.com/threat-intel/v1/url_check \
-H "x-api-key: $REEF_KEY" \
-H "content-type: application/json" \
-d '{"url":"https://github.com/"}'import requests
r = requests.post(
"https://api.reefapi.com/threat-intel/v1/url_check",
headers={"x-api-key": REEF_KEY},
json={
"url": "https://github.com/"
},
)
print(r.json()["data"])const res = await fetch("https://api.reefapi.com/threat-intel/v1/url_check", {
method: "POST",
headers: {
"x-api-key": process.env.REEF_KEY,
"content-type": "application/json",
},
body: JSON.stringify({
"url": "https://github.com/"
}),
});
const { ok, data, meta, error } = await res.json();Ask your MCP-connected assistant: call reefapi.threat-intel.url_check with {"url":"https://github.com/"}.Who uses this API and why
- Anti-abuse systems call url_check to block malicious links in user-generated content in real time.
- Trust-and-safety teams use ip_reputation to score traffic and flag known-bad addresses.
- Security tools use batch to screen a list of domains against multiple threat feeds at once.
Questions developers ask before integrating
github.com is hosting live malware URLs, so why is the verdict clean?
Because the domain is multi-tenant and the flagged content lives at specific paths. A measured domain_reputation on github.com returned verdict clean, score 0 and dedicated_signals 0, while sources[0] reported malware_urls 48, active_malware_urls 21, shared_hosting true, dedicated false, weight 0 and an explicit note that the domain itself is not condemned. threat_types still listed malware_download and malware_urls carried the 48 URLs with their dateadded timestamps. For a host like this, check the exact URL with url_check rather than the domain.
Can score be non-zero while the verdict is clean?
Yes, and that is the normal case for heuristics. The spec's own example URL, an http link with a bare IPv4 host, returned score 10 with flags ["non_https", "ip_literal_host"], an empty sources array, dedicated_signals 0 and verdict clean. Heuristic flags add points because the shape of the URL is suspicious, but no feed reported it. If you gate on score alone you will block ordinary internal HTTP links.
Is a clean verdict authoritative?
No. These are reported-abuse feeds, so clean means nothing is currently listed rather than nothing is wrong. A measured ip_reputation for 8.8.8.8 returned record_count 0, an empty sources array and verdict clean after checking five feeds. Read checked_sources to confirm which lists ran, and pair this with domain-risk when you need a judgment on a domain that is too new to have been reported yet.
The verdict is malicious but the source says status offline. Which is it?
Both. A measured ip_reputation on 162.243.103.246 returned verdict malicious with score 80 from a single Feodo block: malware Emotet, port 8080, as_name DIGITALOCEAN-ASN, country US, first_seen 2022-06-04 and last_online 2026-03-07, with status offline. Feodo keeps historical command-and-control records, so read last_online before treating the address as live infrastructure, and c2_ports if you are writing firewall rules.
What does meta.record_count count here?
Matching source blocks, not indicators. A clean IP returned 0, the github.com URL returned 1 because one informational URLHaus block matched, and a four-target batch returned 4 because batch counts inputs instead. Never read record_count as a threat count; use dedicated_signals for that, or malicious_count on batch.
scan_lookup returned ok true with an empty scans array. Was the domain never scanned?
Not necessarily. urlscan.io's anonymous search is aggressively rate-limited, and a measured github.com lookup returned ok true with stop_reason source_unavailable, total 0, an empty scans array, urlscan_available false and urlscan_status "urlscan rate-limited/blocked (HTTP 429)", plus a note suggesting domain_reputation instead. Branch on urlscan_available rather than on the length of scans, or you will record an unavailable source as a clean history.
How is this different from domain-risk?
threat-intel answers whether anybody has reported this indicator, by consulting block-lists. domain-risk answers whether a domain looks like a fraud setup, from RDAP age, expiry, nameservers, mail records, certificate transparency and lookalike structure, with no block-list involved. A phishing domain registered this morning is typically clean in threat-intel and elevated in domain-risk, so run both when you are scoring an unknown host.
How does batch decide which feeds to run for each entry?
It detects the type of each string and routes it. A measured batch of a URL, a domain, an IP and an IP-literal URL returned four results with different checked_sources arrays, an ok flag and an input echo on each, plus top-level malicious_count 1 and ok_count 4. The cap is 20 indicators per call, and a mixed batch of clean targets came back in about two seconds because the feed snapshots are shared across the entries.
What is the Threat Intelligence API?
Threat Intelligence API is a ReefAPI endpoint group for threat intelligence It returns live JSON through POST requests under /threat-intel/v1.
Is the Threat Intelligence API free to try?
Yes. ReefAPI starts with 1,000 free credits, no card required. Threat Intelligence calls use the same shared credit balance as every other ReefAPI engine.
Do I need a Threat Intelligence login or account?
No login to Threat Intelligence is needed for the API response. You call ReefAPI with your x-api-key header, and the playground can run live examples before you create a production key.
How fresh is the Threat Intelligence data?
The page example is captured from a live url_check call, and production requests fetch live data through ReefAPI rather than a static sample.
How many credits does the Threat Intelligence API use?
Threat Intelligence actions currently cost 1 credit per successful call. Failed or blocked calls are free, and all APIs draw from one credit pool.
Can I call Threat Intelligence from an AI assistant or MCP client?
Yes. Connect ReefAPI once through MCP and your assistant can call threat-intel actions with the same key, credit pool and JSON envelope used by normal REST requests.