ScanMalware REST API Documentation
Complete API reference for integrating website security scanning into your applications
Getting Started
The ScanMalware API provides programmatic access to URL security scanning capabilities. All endpoints return JSON responses and use standard HTTP status codes.
🌐 Base URL
https://scanmalware.com🚀 Quick Example
curl -X POST "https://scanmalware.com/api/v1/scan" \
-H "Content-Type: application/json" \
-d '{"url": "https://example.com"}'📖 Full Documentation Details
Rate Limits
Requests are rate limited per IP address. Sending an API key raises your limit substantially, so authenticate any automated or high-volume use.
- Anonymous: 600 requests/minute to
/api/(60/minute for hash search pages) - With an API key: 3000 requests/minute
Short bursts above these rates are allowed before anything is rejected. Exceeding the limit returns 429 Too Many Requests with a JSON body and a Retry-After header — wait for that many seconds and retry. Create a key on your account page and send it as the X-API-Key header.
Pagination
All search and listing endpoints support pagination to prevent database overload and improve performance. Pagination is implemented using page and limit parameters.
Paginated endpoints include:
/api/v1/recent- Recent scans/api/v1/search- Text search/api/v1/search/asn/{asn_number}- ASN search/api/v1/search/favicon/{hash_value}- Favicon hash search/api/v1/search/screenshot/{hash_type}/{hash_value}- Screenshot hash search/api/v1/search/fuzzy/{hash_type}- Fuzzy hash search/api/v1/search/similar- Similar scans search
All paginated responses include a pagination object:
"pagination": {
"page": 1, // Current page number
"limit": 20, // Items per page
"total_items": 272, // Total number of items
"total_pages": 14, // Total number of pages
"has_next": true, // Whether there's a next page
"has_prev": false // Whether there's a previous page
}Error Handling
The API uses conventional HTTP response codes to indicate success or failure. Error responses include a JSON object with error details.
{
"error": "Invalid URL provided",
"code": 400,
"details": "The URL must be a valid HTTP or HTTPS URL"
}Finding subdomains of a domain
Several endpoints return hostnames beneath a domain, but they answer different questions and differ by more than an order of magnitude in coverage. Start with /api/v1/ct/dns/{domain} — the others are corroboration or a different question entirely.
| Request | Answers | hkr.se | cloudflare.com |
|---|---|---|---|
GET /api/v1/ct/dns/{domain} | Every hostname seen in CT-derived DNS data. The enumeration source. | 68 | 1053 |
GET /api/v1/ct/{domain} | Hostnames that hold a certificate, with the attesting cert. Capped at 100 certs. | 6 | 28 |
GET /api/v1/search/smql?q=domain:*.{domain} | Which subdomains have been scanned — not which exist. | 1 | 97 |
GET /api/v1/tls/{scan_id} | SANs on the certificate actually served. The only source of wildcard names. | 1 | 0 |
GET /api/v1/ct/ip/{ip} | Hostnames sharing one IP. Yields subdomains only when they share it. | 0 | 4 |
GET /api/v1/domains/{domain}/scans | Scans recorded for the domain and its subdomains. | 1 | 15 |
GET /api/v1/hosts/{domain} | Every host we have seen for a domain, grouped by evidence: what the browser contacted, plus subdomains a third party asked us about that we confirmed resolve. | 4 | 155 |
Measured 2026-08-22. Counts are distinct hostnames beneath the apex./ct/similar, /ct/timeline, /domain/stats and /search?q= return none and are not subdomain sources.
Recipe
# 1. Enumerate. Raise the cap for wide domains and always check the flag.
curl -s "https://scanmalware.com/api/v1/ct/dns/$D?subdomain_limit=5000" \
| jq '{n: .subdomain_count, truncated: .subdomains_truncated, hosts: .subdomains}'
# 2. Dangling DNS: published in a certificate, no longer resolving.
# These are subdomain-takeover candidates.
curl -s "https://scanmalware.com/api/v1/ct/dns/$D" \
| jq -r '.dns_records[] | select(.resolution_error=="nxdomain") | .domain'
# 3. Wildcard names, which never resolve and so never appear above.
curl -s "https://scanmalware.com/api/v1/tls/$SCAN_ID" | jq -r '.sans.dns_names[]'
# 4. Which of them have actually been scanned.
curl -s -G "https://scanmalware.com/api/v1/search/smql" \
--data-urlencode "q=domain:*.$D" --data-urlencode 'limit=100'Three things that will bite you otherwise:
subdomainsis capped atsubdomain_limit(default 2000, max 5000). Always readsubdomains_truncated— a partial list is otherwise indistinguishable from a complete short one.- A record's
ipis often empty and that is meaningful: the hostname was in a certificate but did not resolve.resolution_errorsays why. Do not discard those — they are the interesting ones. - SMQL searches the scan corpus, not DNS. For hkr.se that is 1 host against 68 that exist. It answers "what have we looked at".
SMQL search filters
Every filter accepted by GET /api/v1/search/smql?q=<query> and by Advanced search: 127 filters and 20 has: checks. The live list, with the same fields, is GET /api/v1/search/smql/filters.
Syntax
| text search | paypal login |
| filter | field:value |
| quoted | field:"value with spaces" |
| comparison | field:>value, field:<value, field:>=value, field:<=value |
| range | field:value1..value2 |
| wildcard | field:*.example.com |
| boolean | filter1 AND filter2, filter1 OR filter2 |
| negation | -field:value or NOT field:value |
| grouping | (filter1 OR filter2) AND filter3 |
| existence | has:feature |
Core (14)
| Filter | Description | Example |
|---|---|---|
urltext · wildcard | URL (substring match against the entry and final URL) | url:paypal.com |
domaintext · wildcard | Extracted domain name | domain:paypal.com |
titletext · wildcard | Page title (substring match) | title:login |
nodriver_titletext · wildcard | Residential (VPN-egress) capture page title (substring match). Differs from `title` (the datacenter capture) when a site cloaks scanners — a scanner-cloaking phishing lure surfaces here even when the datacenter title is a decoy shell or a redirect target. | nodriver_title:"Meta for Business" |
scan_idtext | Exact scan ID (the /result/<id> identifier). Mainly useful to scope another query to a single scan, e.g. checking whether a specific scan matches a hunt anchor. | scan_id:c7df0db2-ca1d-423c-866f-80d4cb3a43db |
statusenum | Scan status Values: completed, failed, error, queued, processing | status:completed |
scan_typeenum | Scan visibility type Values: public, unlisted, private | scan_type:public |
workertext | Worker ID that processed the scan | worker:chrome-worker-1 |
load_timefloat · compare · range | Page load time in seconds | load_time:>5 |
submitteddate · compare · range | Scan submission timestamp | submitted:last7d |
completeddate · compare · range | Scan completion timestamp | completed:>2024-01-01 |
errortext | Error message text | error:timeout |
proxybool | Whether a proxy was used | proxy:true |
http_statusint · compare · range | HTTP response status code in any transaction (200, 301, 403, 404, 500, etc.) | http_status:403 |
Network (7)
| Filter | Description | Example |
|---|---|---|
ipinet | Server IP address (supports CIDR notation) | ip:1.1.1.1 |
primary_ipinet | Primary server IP address (supports CIDR notation) | primary_ip:1.1.1.1 |
asnint | Autonomous System Number | asn:13335 |
asn_orgtext | ASN organization name | asn_org:Cloudflare |
countrytext | ISO 2-letter country code | country:US |
citytext | City name | city:"New York" |
ip_countint · compare · range | Number of unique IPs contacted | ip_count:>10 |
WHOIS (8)
| Filter | Description | Example |
|---|---|---|
registrartext · wildcard | Domain registrar name | registrar:namecheap |
domain_ageint · compare · range | Domain age in days (since registration) | domain_age:<30 |
registration_datedate · compare · range | Domain registration date | registration_date:>2024-01-01 |
expiration_datedate · compare · range | Domain expiration date | expiration_date:<2024-12-31 |
whois_servertext | WHOIS server used for lookup | whois_server:whois.namecheap.com |
nameservertext · wildcard | Nameserver hostname (from RDAP data) | nameserver:ns1.cloudflare.com |
rirenum | Regional Internet Registry Values: RIPE, ARIN, APNIC, LACNIC, AFRINIC | rir:RIPE |
ip_networkcidr | IP network CIDR block (from RDAP) | ip_network:104.16.0.0/12 |
Security (12)
| Filter | Description | Example |
|---|---|---|
verdictenum | AI security classification Values: LEGITIMATE, LOW_RISK, MODERATE_RISK, HIGH_RISK, CONFIRMED_SCAM, NOT_ASSESSED | verdict:HIGH_RISK |
ai_risk_scoreint · compare · range | AI risk score (0-100) | ai_risk_score:>50 |
ai_confidenceint · compare · range | AI confidence percentage (0-100) | ai_confidence:>80 |
device_code_phishingbool | AI flagged device-code / OAuth-consent (EvilToken) phishing | device_code_phishing:true |
categorytext | Content category (ML classification) | category:"phishing scam" |
safe_browsingenum | Google Safe Browsing threat type Values: MALWARE, SOCIAL_ENGINEERING, UNWANTED_SOFTWARE | safe_browsing:MALWARE |
clamavenum | ClamAV scan result Values: clean, infected | clamav:infected |
virustext · wildcard | ClamAV virus/malware name | virus:Trojan |
ioctext | IOC indicator value | ioc:evil.com |
ioc_typeenum | IOC indicator type Values: ip, domain, hash, url, email | ioc_type:domain |
threat_feedtext | Threat intelligence feed source | threat_feed:OTX |
rpkienum | RPKI BGP origin validation status Values: valid, invalid, not-found | rpki:invalid |
TLS (23)
| Filter | Description | Example |
|---|---|---|
cert_issuertext · wildcard | Certificate issuer (CN or organization) | cert_issuer:"Let's Encrypt" |
cert_subjecttext · wildcard | Certificate subject common name | cert_subject:*.example.com |
cert_orgtext | Certificate subject organization | cert_org:"Google LLC" |
cert_expiredbool | Certificate is expired | cert_expired:true |
cert_self_signedbool | Certificate is self-signed | cert_self_signed:true |
cert_wildcardbool | Certificate is wildcard | cert_wildcard:true |
cert_evbool | Extended Validation certificate | cert_ev:true |
cert_lets_encryptbool | Let's Encrypt certificate | cert_lets_encrypt:true |
cert_validbool | Certificate chain is valid | cert_valid:false |
cert_revokedbool | Certificate is revoked | cert_revoked:true |
cert_weak_keybool | Weak cryptographic key detected | cert_weak_key:true |
tls_algorithmtext | TLS signature algorithm | tls_algorithm:SHA256withRSA |
key_algorithmtext | Public key algorithm | key_algorithm:RSA |
key_sizeint · compare · range | Public key size in bits (use with key_algorithm for meaningful results, e.g. key_algorithm:RSA key_size:<2048) | key_size:<2048 |
cert_daysint · compare · range | Days until certificate expiry | cert_days:<30 |
cert_fingerprinttext | Certificate SHA-256 fingerprint (hex; case, colons and spaces ignored) | cert_fingerprint:f63a5fa3717eadd1d7842690d859152eb53b081eb92f859b0a84d6bda43d2fb5 |
cert_sha1text | Certificate SHA-1 fingerprint, as shown in Certificate Transparency logs (hex; case, colons and spaces ignored) | cert_sha1:1992148f71c2c6ceea8e6b882182cb9fbbad7400 |
ja4xtext · wildcard | JA4X structural certificate fingerprint (issuer RDNs_subject RDNs_extensions). Describes how a certificate is BUILT, so it survives every string in it changing. The EXTENSION half (last segment) is the discriminating one - match it as a suffix, e.g. ja4x:*5318375af521. Avoid writing the separator in a wildcard pattern: SQL LIKE treats _ as a single-character wildcard, so *_5318375af521 is silently broader than it looks. | ja4x:2bab15409345_2bab15409345_5318375af521 |
cert_riskint · compare · range | Certificate risk score (0-100) | cert_risk:>60 |
cert_sharedint · compare · range | Number of domains sharing this certificate | cert_shared:>100 |
caabool | Has CAA DNS records | caa:true |
caa_compliantbool | Certificate is CAA compliant | caa_compliant:false |
ct_loggedbool | Certificate is in CT logs | ct_logged:false |
JARM (2)
| Filter | Description | Example |
|---|---|---|
jarmtext | JARM TLS fingerprint hash | jarm:29d29d15d29d29d... |
jarm_knownbool | Matches a known JARM signature | jarm_known:true |
Technology (4)
| Filter | Description | Example |
|---|---|---|
technologytext · wildcard | Detected technology name | technology:WordPress |
tech_categorytext | Technology category | tech_category:cms |
tech_versiontext | Technology version | tech_version:1.12 |
cpetext · wildcard | CPE identifier | cpe:cpe:2.3:a:wordpress* |
JavaScript (19)
| Filter | Description | Example |
|---|---|---|
js_riskenum | JS obfuscation risk level Values: low, medium, high, critical | js_risk:high |
js_risk_scoreint · compare · range | JS max risk score (0-100) | js_risk_score:>70 |
js_evalint · compare | Number of eval() calls detected | js_eval:>0 |
js_func_constructorint · compare | Function() constructor calls | js_func_constructor:>0 |
js_hashtext | JS code segment SHA-256 hash | js_hash:a1b2c3d4e5f6... |
js_tlshtext | JS code segment TLSH fuzzy hash | js_tlsh:T1A1B2C3D4... |
js_librarytext · wildcard | Matched JavaScript library name | js_library:jquery |
js_suspiciousbool | JS segment flagged as suspicious | js_suspicious:true |
js_obfuscatedbool | JavaScript is obfuscated | js_obfuscated:true |
obfuscation_scoreint · compare · range | Obfuscation risk score (0-100) | obfuscation_score:>50 |
js_cdntext | CDN type serving the JavaScript | js_cdn:cloudflare |
js_servertext | HTTP server type for JavaScript | js_server:nginx |
js_npmtext | NPM package name | js_npm:react |
fp_canonicaltext | js-fp3 canonical AST hash — the obfuscation-resistant identity (identifier-renamed copies collapse to one hash) | fp_canonical:4a624378be31194f607a8011f974f6bacc322d44077c507c1f431a3ae3b31b6b |
fp_contenttext | js-fp3 content SHA-256 — byte-identical script (or webpack module) occurrence | fp_content:e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855 |
fp_tlshtext | js-fp3 TLSH (locality-sensitive hash) — near-duplicate by fuzzy hash | fp_tlsh:T1A21206E2… |
similar_totext | js-fp3 structurally similar script — scans containing one of the 1000 nearest occurrences (cosine ≥ 0.7 on the Layer-3 vector) to the script identified by the given canonical_ast_hash anchor | similar_to:4a624378be31194f607a8011f974f6bacc322d44077c507c1f431a3ae3b31b6b |
malware_familytext | Malware pattern category | malware_family:miner |
malware_patterntext | Malware pattern name | malware_pattern:CoinHive |
Hashes (9)
| Filter | Description | Example |
|---|---|---|
phashtext | Perceptual screenshot hash | phash:a1b2c3d4e5f6 |
dhashtext | Difference screenshot hash | dhash:f0e1d2c3b4a5 |
ahashtext | Average screenshot hash | ahash:a1b2c3d4e5f6 |
whashtext | Wavelet screenshot hash | whash:a1b2c3d4e5f6 |
color_hashtext | Screenshot color hash | color_hash:#a1b2c3 |
favicon_hashtext | Favicon MMH3 hash | favicon_hash:-12345678 |
tlshtext | TLSH fuzzy hash of page content (exact match) | tlsh:T1CA048E77329A063986558498E057430D9F20B543B50ACDBC7ABCBAD8BFDED06107BB78 |
ssdeeptext | ssdeep fuzzy hash of page content (exact match) | ssdeep:3072:VfQho9PKBb9JsE9RHCbZgRjFtSBaw9QWg:yhoC9J395CbZgLtSL3gc |
favicon_md5text | Favicon MD5 hash | favicon_md5:d41d8cd98f00b204e9800998ecf8427e |
Tracking (4)
| Filter | Description | Example |
|---|---|---|
trackertext | Tracker type | tracker:google_analytics |
tracking_idtext | Specific tracking ID | tracking_id:UA-12345678 |
tracker_categorytext | Tracker category | tracker_category:analytics |
tracker_risktext | Tracker risk level | tracker_risk:high |
Content (16)
| Filter | Description | Example |
|---|---|---|
ocrtext · wildcard | OCR text from screenshot | ocr:"verify your account" |
ocr_languagetext | OCR detected language | ocr_language:en |
pastejacking_severityenum | Pastejacking severity level Values: low, medium, high, critical | pastejacking_severity:high |
bot_detectiontext | Bot protection type encountered | bot_detection:cloudflare |
bot_evasionbool | Bot evasion was attempted | bot_evasion:true |
is_clonebool | Detected as a clone of a legitimate site | is_clone:true |
clone_scorefloat · compare | Clone similarity score | clone_score:>0.8 |
clearfake_typetext | ClearFake detection type | clearfake_type:eval_atob |
ids_signaturetext · wildcard | Suricata IDS signature name | ids_signature:"ET TROJAN" |
ids_categorytext | IDS alert category | ids_category:"A Network Trojan was detected" |
ids_severityint · compare | IDS alert severity (1=highest, 4=lowest) | ids_severity:1 |
ids_alertsint · compare | Total IDS alert count | ids_alerts:>0 |
bundlertext | JavaScript bundler type | bundler:webpack |
bundle_modulesint · compare | Number of modules in bundle | bundle_modules:>50 |
warning_pagebool | Browser warning page was detected | warning_page:true |
warning_typetext | Warning page type | warning_type:deceptive_site |
Hosts (4)
| Filter | Description | Example |
|---|---|---|
contacted_hosttext · wildcard | Host the browser actually resolved and requested during the scan. Observed evidence. Supports *.example.com for subdomain queries. | contacted_host:cdnjs.cloudflare.com |
csp_hosttext · wildcard | Host named in the page's Content-Security-Policy. DECLARED intent, not contact — the page may never have talked to it. Supports wildcards. | csp_host:*.github.com |
script_hosttext · wildcard | Host of a script the browser actually loaded. Observed evidence. Supports wildcards. | script_host:cdn.jsdelivr.net |
js_hosttext · wildcard | Host called from a URL sink inside script source (fetch/open/WebSocket/...). STATIC finding — roughly a third are corroborated by runtime, the rest being conditional or dead code. Supports wildcards. | js_host:sentry.io |
CT (5)
| Filter | Description | Example |
|---|---|---|
ct_domaintext · wildcard | Domain in Certificate Transparency logs | ct_domain:*.paypal.com |
ct_santext | Certificate Subject Alternative Name | ct_san:*.example.com |
ct_hashtext | Certificate hash in CT logs | ct_hash:abc123... |
ct_logtext | CT log source | ct_log:Google |
ct_issueddate · compare · range | Certificate issuance date in CT | ct_issued:>2024-01-01 |
Existence checks (20)
has:malware | Malware detected by ClamAV |
has:tracker | Has tracking codes |
has:pastejacking | Pastejacking detected |
has:ioc | Has IOC threat intelligence matches |
has:jarm | Has JARM TLS fingerprint |
has:certificate | Has TLS certificate data |
has:screenshot | Has screenshot |
has:ocr | Has OCR text extracted |
has:bot_detection | Bot protection was encountered |
has:safe_browsing | Flagged by Google Safe Browsing |
has:clipboard | Has clipboard events |
has:clone | Detected as a clone site |
has:clearfake | ClearFake attack detected |
has:ids | Has IDS/Suricata alerts |
has:rpki_invalid | Has RPKI invalid result |
has:pcap | Has decrypted PCAP capture |
has:fallback | Has fallback scan (bot bypass) |
has:whois | Has WHOIS/RDAP domain data |
has:webpack | Has webpack/rollup bundle |
has:phishing | Has phishing detection result |
API Endpoints
/api/v1/scanSubmit URL for Scanning
Submit a URL for scanning. Works anonymously for public and unlisted scans. Authenticate with a Bearer token (when logged in) or an API key with the scan:submit scope (X-API-Key header, created on your account page) to attribute the scan to your account; private scans require authentication and are visible only to you.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
url | string | Required | |
scan_type | string | Optional | |
options | string | Optional | |
csrf_token | string | Optional |
Response
{
"scan_id": "string",
"status": "string",
"message": "string",
"scan_type": "string",
"submitted_at": "string"
}Example
Request
curl -X POST "https://scanmalware.com/api/v1/scan" \
-H "Content-Type: application/json" \
-d '{"url": "https://example.com", "scan_type": "public"}'Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"status": "queued",
"message": "Scan submitted successfully",
"scan_type": "public",
"submitted_at": "2025-08-20T16:30:00.000Z"
}/api/v1/result/{scan_id}Get Scan Results
Retrieve the results of a specific scan. Private scans are returned only to their owner — authenticate with a Bearer token or an API key with the scan:read scope (X-API-Key header); other callers receive 404.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"url": "string",
"status": "string",
"scan_type": "string",
"submitted_at": "string",
"completed_at": "string",
"results": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/result/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"status": "completed",
"scan_type": "public",
"submitted_at": "2025-08-20T16:30:00.000Z",
"completed_at": "2025-08-20T16:30:15.000Z",
"results": {
"title": "Example Domain",
"screenshot_path": "screenshots/123e4567.png",
"technologies": [...],
"network_requests": [...],
"security_analysis": {...}
}
}/api/v1/account/overviewAccount Overview
Headline stats for your account: total scans, scans this month, active API keys and last login. Requires a Bearer token (log in on scanmalware.com; API keys are not accepted on account-management endpoints).
Response
{
"total_scans": "number",
"scans_this_month": "number",
"active_api_keys": "number",
"last_login": "number",
"user": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/account/overview" \
-H "Authorization: Bearer $TOKEN"Response
{
"total_scans": 42,
"scans_this_month": 7,
"active_api_keys": 2,
"last_login": 1781099789662,
"user": {"username": "[email protected]", "email": "[email protected]"}
}/api/v1/account/scansList Your Scans
Your submitted scans (including unlisted and private), newest first, with pagination. Requires a Bearer token.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
page | integer | Optional | Page number (default 1) |
limit | integer | Optional | Items per page (default 20, max 100) |
Response
{
"results": "array",
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/account/scans?page=1&limit=20" \
-H "Authorization: Bearer $TOKEN"Response
{
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"status": "completed",
"scan_type": "private",
"submitted_at": "2026-06-10T13:57:22",
"verdict": "Safe",
"risk_level": "low"
}
],
"pagination": {"page": 1, "limit": 20, "total_items": 1, "total_pages": 1}
}/api/v1/account/loginsRecent Logins
Your recent login events (time, result, IP address, application). Requires a Bearer token.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
limit | integer | Optional | Max events to return (default 20, max 100) |
Response
{
"available": "boolean",
"logins": "array"
}Example
Request
curl "https://scanmalware.com/api/v1/account/logins?limit=20" \
-H "Authorization: Bearer $TOKEN"Response
{
"available": true,
"logins": [
{"time": 1781099789662, "type": "LOGIN", "ip_address": "203.0.113.7", "client": "scanmalware-frontend"}
]
}/api/v1/account/api-keysList API Keys
Your non-revoked API keys (the secret part is never shown again after creation). Requires a Bearer token.
Response
{
"api_keys": "array"
}Example
Request
curl "https://scanmalware.com/api/v1/account/api-keys" \
-H "Authorization: Bearer $TOKEN"Response
{
"api_keys": [
{
"id": "f24ba539-b11a-41bc-a3a2-95323b17bc69",
"name": "CI pipeline",
"token_prefix": "sm_pat_390eb0790370",
"scopes": ["scan:submit"],
"created_at": "2026-06-10T13:56:54+00:00",
"expires_at": "2026-09-08T13:56:54+00:00",
"last_used_at": null,
"is_expired": false
}
]
}/api/v1/account/api-keysCreate API Key
Create a personal access token for programmatic API access (X-API-Key header). The full token is returned ONCE in this response — store it immediately. Scopes: scan:submit (submit scans), scan:read (read your scans incl. private). Expiration defaults to 90 days; pass null for a non-expiring key. Maximum 10 active keys. Requires a Bearer token.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
name | string | Required | A label for the key (e.g. "CI pipeline") |
scopes | array | Optional | Subset of ["scan:submit", "scan:read"]; defaults to ["scan:submit"] |
expires_in_days | integer | Optional | Days until expiry (default 90); null = never expires |
Response
{
"id": "string",
"name": "string",
"token_prefix": "string",
"scopes": "array",
"created_at": "string",
"expires_at": "string",
"api_key": "string",
"notice": "string"
}Example
Request
curl -X POST "https://scanmalware.com/api/v1/account/api-keys" \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{"name": "CI pipeline", "scopes": ["scan:submit", "scan:read"], "expires_in_days": 90}'Response
{
"id": "f24ba539-b11a-41bc-a3a2-95323b17bc69",
"name": "CI pipeline",
"token_prefix": "sm_pat_390eb0790370",
"scopes": ["scan:read", "scan:submit"],
"created_at": "2026-06-10T13:56:54+00:00",
"expires_at": "2026-09-08T13:56:54+00:00",
"api_key": "sm_pat_390eb0790370_<secret — shown only once>",
"notice": "Store this token now — it will not be shown again."
}/api/v1/account/api-keys/{key_id}Revoke API Key
Revoke one of your API keys. Takes effect immediately. Requires a Bearer token.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
key_id | string | Required | The key's id (from the list endpoint) |
Response
{
"revoked": "boolean",
"id": "string"
}Example
Request
curl -X DELETE "https://scanmalware.com/api/v1/account/api-keys/f24ba539-b11a-41bc-a3a2-95323b17bc69" \
-H "Authorization: Bearer $TOKEN"Response
{"revoked": true, "id": "f24ba539-b11a-41bc-a3a2-95323b17bc69"}/api/v1/account/api-keys/revoke-allRevoke All API Keys
Emergency revocation of ALL your API keys at once (e.g. after a suspected leak). Requires a Bearer token.
Response
{
"revoked": "boolean",
"count": "number"
}Example
Request
curl -X POST "https://scanmalware.com/api/v1/account/api-keys/revoke-all" \
-H "Authorization: Bearer $TOKEN"Response
{"revoked": true, "count": 3}/api/v1/account/api-keys/auditAPI Key Audit Trail
Audit log for your API keys: creation, revocation, and successful/failed authentications, newest first. Requires a Bearer token.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
limit | integer | Optional | Max events to return (default 50, max 200) |
Response
{
"events": "array"
}Example
Request
curl "https://scanmalware.com/api/v1/account/api-keys/audit?limit=50" \
-H "Authorization: Bearer $TOKEN"Response
{
"events": [
{"event": "auth_success", "key_name": "CI pipeline", "token_prefix": "sm_pat_390eb0790370", "ip_address": "203.0.113.7", "time": "2026-06-10T14:17:18+00:00"}
]
}/api/v1/scan/{scan_id}/summaryGet Scan Summary
Get condensed scan information for integrations
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"url": "string",
"final_url": "string",
"status": "string",
"completed_at": "string",
"security_verdict": {
"overall_score": "integer",
"risk_level": "string"
},
"risk_score": "integer",
"technologies_count": "integer",
"tracker_count": "integer",
"redirect_count": "integer",
"certificate_valid": "boolean",
"load_time": "number"
}Example
Request
curl "https://scanmalware.com/api/v1/scan/123e4567-e89b-12d3-a456-426614174000/summary"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"final_url": "https://www.example.com",
"status": "completed",
"completed_at": "2025-08-20T16:30:15.000Z",
"security_verdict": {
"overall_score": 15,
"risk_level": "safe"
},
"risk_score": 85,
"technologies_count": 5,
"tracker_count": 2,
"redirect_count": 1,
"certificate_valid": true,
"load_time": 1.234
}/api/v1/domains/{domain}/scansDomain History
Public scans of a domain and its subdomains, matched on the scanned host — the entry host, the final host after redirects, or a subdomain of either. `matched_on` says which side matched, so a scan that STARTED here is distinguishable from one that only REDIRECTED here. The domain must appear as a whole label: a host that merely contains the string does not match, and neither does the domain appearing in a path or query string. Returns a JSON array (only public scans are available via API).
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
domain | string | Required | The domain to search for (e.g., "example.com") |
status | string | Optional | Filter by scan status: "queued", "processing", "completed", or "failed" |
limit | integer | Optional | Number of results (1-100, default: 20) |
Response
[
{
"scan_id": "string",
"url": "string",
"final_url": "string | null",
"matched_on": "array of \"url\" and/or \"final_url\"",
"status": "string",
"scan_type": "string",
"submitted_at": "string",
"completed_at": "string | null",
"title": "string"
}
]Example
Request
curl "https://scanmalware.com/api/v1/domains/example.com/scans?status=completed&limit=10"Response
[
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"final_url": "https://example.com/",
"matched_on": [
"url",
"final_url"
],
"status": "completed",
"scan_type": "public",
"submitted_at": "2025-08-20T16:30:00.000Z",
"completed_at": "2025-08-20T16:30:15.000Z",
"title": "Example Domain"
},
{
"scan_id": "223e4567-e89b-12d3-a456-426614174001",
"url": "https://links.test/abcd",
"final_url": "https://docs.example.com/start",
"matched_on": [
"final_url"
],
"status": "completed",
"scan_type": "public",
"submitted_at": "2025-08-20T14:02:11.000Z",
"completed_at": "2025-08-20T14:02:29.000Z",
"title": "Getting started"
}
]/api/v1/recentGet Recent Public Scans
Retrieve a list of recent public scans with pagination (only public scans are available via API)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"results": [
{
"scan_id": "string",
"url": "string",
"status": "string",
"scan_type": "string",
"submitted_at": "string",
"title": "string"
}
],
"pagination": {
"page": "integer",
"limit": "integer",
"total_items": "integer",
"total_pages": "integer",
"has_next": "boolean",
"has_prev": "boolean"
}
}Example
Request
curl "https://scanmalware.com/api/v1/recent?page=1&limit=10"Response
{
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"status": "completed",
"scan_type": "public",
"submitted_at": "2025-08-20T16:30:00.000Z",
"title": "Example Domain"
}
],
"pagination": {
"page": 1,
"limit": 10,
"total_items": 272,
"total_pages": 28,
"has_next": true,
"has_prev": false
}
}/api/v1/searchSearch Scans
Search through public scan results only
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
q | string | Required | Search query (minimum 3 characters) |
type | string | Optional | Search type: "url", "domain", "title", "technology", or "all" (default: "all") |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
[
{
"scan_id": "string",
"url": "string",
"status": "string",
"scan_type": "string",
"submitted_at": "string",
"title": "string"
}
]Example
Request
curl "https://scanmalware.com/api/v1/search?q=example.com&type=domain"Response
[
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"status": "completed",
"scan_type": "public",
"submitted_at": "2025-08-20T16:30:00.000Z",
"title": "Example Domain"
}
]/api/v1/search/asn/{asn_number}Search by ASN
Search for public scans from a specific Autonomous System Number (ASN)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
asn_number | integer | Required | The AS number to search for without AS prefix (e.g., 13335 for Cloudflare, not AS13335) |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 50, max: 500) |
Response
{
"asn": "integer",
"organization": "string",
"total_scans": "integer",
"unique_urls": "integer",
"first_seen": "string | null",
"last_seen": "string | null",
"results": [
{
"scan_id": "string",
"url": "string",
"status": "string",
"scan_type": "string",
"submitted_at": "string",
"title": "string",
"primary_asn": "integer",
"asn_org": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/search/asn/13335"Response
{
"asn": 13335,
"organization": "CLOUDFLARENET",
"total_scans": 42,
"unique_urls": 35,
"first_seen": "2025-08-19T10:00:00.000Z",
"last_seen": "2025-08-20T16:30:00.000Z",
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"status": "completed",
"scan_type": "public",
"submitted_at": "2025-08-20T16:30:00.000Z",
"title": "Example Domain",
"primary_asn": 13335,
"asn_org": "CLOUDFLARENET"
}
]
}/api/v1/search/favicon/{hash_value}Search by Favicon Hash
Search for websites with the same favicon hash (supports both MMH3 and MD5 hashes)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_value | string | Required | The favicon hash value (MMH3 integer or MD5 hex string) |
hash_type | string | Optional | Hash type: "mmh3" or "md5" (default: "mmh3") |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"hash_type": "string",
"hash_value": "string",
"results": [
{
"scan_id": "string",
"url": "string",
"final_url": "string",
"title": "string",
"submitted_at": "string",
"favicon_mmh3": "string",
"favicon_md5": "string"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/search/favicon/2755474283?hash_type=mmh3"
# Search by MD5 hash
curl "https://scanmalware.com/api/v1/search/favicon/b2ccd167c908a44e1dd69df79382286a?hash_type=md5"Response
{
"hash_type": "mmh3",
"hash_value": "2755474283",
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://www.linkedin.com/",
"final_url": "https://www.linkedin.com/",
"title": "LinkedIn: Log In or Sign Up",
"submitted_at": "2025-08-20T16:30:00.000Z",
"favicon_mmh3": "2755474283",
"favicon_md5": "b2ccd167c908a44e1dd69df79382286a"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total_items": 4,
"total_pages": 1,
"has_next": false,
"has_prev": false
}
}/api/v1/favicon/{scan_id}Get Favicon
Download the favicon image for a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
Binary image data (PNG/ICO format) or 404 if no favicon foundExample
Request
curl "https://scanmalware.com/api/v1/favicon/123e4567-e89b-12d3-a456-426614174000" --output favicon.pngResponse
Binary image data/api/v1/favicon/search/{mmh3_hash}Search by MMH3 Favicon Hash
Search for scans with a specific MMH3 favicon hash
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
mmh3_hash | string | Required | The MMH3 hash value |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"mmh3_hash": "string",
"results": [
{
"scan_id": "string",
"url": "string",
"final_url": "string",
"title": "string",
"submitted_at": "string",
"favicon_mmh3": "string",
"favicon_md5": "string"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/favicon/search/2755474283"Response
{
"mmh3_hash": "2755474283",
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://www.linkedin.com/",
"final_url": "https://www.linkedin.com/",
"title": "LinkedIn: Log In or Sign Up",
"submitted_at": "2025-08-20T16:30:00.000Z",
"favicon_mmh3": "2755474283",
"favicon_md5": "b2ccd167c908a44e1dd69df79382286a"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total_items": 4,
"total_pages": 1,
"has_next": false,
"has_prev": false
}
}/api/v1/favicon/statsFavicon Statistics
Get statistics about favicon detection and hashes
Response
{
"total_favicons": "integer",
"recent_24h_favicons": "integer",
"most_common_hashes": [
{
"hash": "integer",
"count": "integer",
"sample_urls": [
"string"
]
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/favicon/stats"Response
{
"total_favicons": 214978,
"recent_24h_favicons": 422,
"most_common_hashes": [
{
"hash": 1007520286,
"count": 10428,
"sample_urls": [
"http://00k-ny8-327hi-c2lc-f65-yogh2g.pages.dev/",
"http://03nlvk-3xo43-lut5i-lu9-n95ug.pages.dev/"
]
},
{
"hash": -949618468,
"count": 4108,
"sample_urls": [
"http://07nan-yqrvso-qicd45-syx8.pages.dev/",
"http://09aieh-zyd-j90-ba8-r2jh-insll.pages.dev/"
]
}
]
}/api/v1/search/screenshot/{hash_type}/{hash_value}Search by Screenshot Hash
Search for scans by screenshot hash (public scans only)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_type | string | Required | Hash type: "ahash", "phash", "dhash", "whash", "color_hash", or "crop_resistant" |
hash_value | string | Required | The hash value to search for |
similarity_threshold | integer | Optional | Hamming distance threshold for similarity search (0-64, perceptual hashes only) |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"hash_type": "string",
"hash_value": "string",
"count": "integer",
"results": [
{
"scan_id": "string",
"url": "string",
"title": "string",
"submitted_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/search/screenshot/phash/1a2b3c4d5e6f7890"Response
{
"hash_type": "phash",
"hash_value": "1a2b3c4d5e6f7890",
"count": 1,
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"title": "Example Domain",
"submitted_at": "2025-08-20T16:30:00.000Z"
}
]
}/api/v1/screenshot/searchScreenshot Hash Search
Search for visually similar screenshots using perceptual hashing. Returns scans whose screenshot hash is within `max_distance` bits of the one given, closest first. `hash_type` is one of phash, ahash, dhash, whash. ⚠️ THIS RETURNED [] FOR EVERY INPUT until 2026-08-29, and the cause is worth keeping written down. It read the BARE `screenshot_hashes->>'<type>' key and did `int(stored, 16)`. That key holds a 64-character BIT STRING on 91.6% of rows (see utils/screenshot_hash.py), and 64 binary digits parsed as hex is a 256-BIT number, so the XOR against a 64-bit input always exceeded max_distance. The 8.4% of rows that do store hex were only reachable inside the newest 10,000 scans, which the old query capped itself to. Reported by the MISP maintainers. The comparison now runs in SQL over the whole public corpus (~1.4s), reading the hash through the canonical accessor rather than the ambiguous bare key.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_value | integer | Required | The perceptual hash value as an integer |
hash_type | string | Optional | Hash type (phash, ahash, dhash, whash, crop_resistant). Default: phash |
max_distance | integer | Optional | Maximum hamming distance (1-10, default: 3) |
limit | integer | Optional | Maximum results (1-100, default: 20) |
Response
[
{
"scan_id": "string",
"url": "string",
"title": "string",
"submitted_at": "string",
"similarity_score": "integer",
"ahash_distance": "integer",
"phash_distance": "integer",
"dhash_distance": "integer",
"whash_distance": "integer"
}
]Example
Request
curl -X POST "https://scanmalware.com/api/v1/screenshot/search" \
-H "Content-Type: application/json" \
-d '{"hash_value": 17918433939200614400, "hash_type": "ahash", "max_distance": 5}'Response
[
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"title": "Example Domain",
"submitted_at": "2025-08-20T16:30:00.000Z",
"similarity_score": 95,
"ahash_distance": 3,
"phash_distance": 2,
"dhash_distance": 4,
"whash_distance": 5
}
]/api/v1/screenshot/duplicatesFind Duplicate Screenshots
Group public scans that share a byte-identical perceptual screenshot hash — useful for spotting phishing kits and hosting placeholders deployed across many hosts. Only exact matches are supported: max_distance must be 0 (its default), because fuzzy matching across the whole screenshot corpus is an O(n²) comparison. To find screenshots similar to one specific hash, use /api/v1/search/screenshot/phash/{hash}?threshold=5 instead. limit pages over GROUPS; max_group_members caps how many scans are listed inside each group. Groups are routinely in the thousands, so every member carries its group's true size in group_size.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_type | string | Optional | |
max_distance | integer | Optional | Exact matches only — 0 is the only accepted value. Grouping the whole corpus by approximate hash is an O(n^2) comparison across 500K+ screenshots and is not implemented. To find screenshots SIMILAR to one specific hash, use GET /api/v1/search/screenshot/{hash_type}/{hash} with its `similarity_threshold` parameter (0-64 bits), which is a linear scan and takes ~1.4s. The bound used to advertise 0-5 while the handler rejected everything above 0, so a spec-generated client emitted requests that could never succeed. |
min_group_size | integer | Optional | |
max_group_members | integer | Optional | Maximum scans returned per duplicate group. Groups of exact screenshot matches are routinely in the thousands (the largest on record holds ~9,000 identical hosting placeholder pages), so this is capped independently of `limit`, which counts GROUPS. Each member carries the group's true size in `group_size`. |
page | integer | Optional | Page number |
limit | integer | Optional | Number of GROUPS per page |
Response
{
"groups": [
"array"
],
"pagination": {
"page": "integer",
"limit": "integer",
"total_groups": "integer",
"total_pages": "integer",
"has_next": "boolean",
"has_prev": "boolean"
},
"generated_at": "string",
"note": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/screenshot/duplicates?hash_type=phash&min_group_size=2&max_group_members=2&limit=1"Response
{
"groups": [
[
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://admin-panel-bpr-exc.pages.dev/about",
"title": "Suspected Phishing | Cloudflare",
"submitted_at": "2026-09-02T16:50:03.542277",
"screenshot": "/api/v1/screenshot/123e4567-e89b-12d3-a456-426614174000.png",
"distance": 0,
"hash_match_type": "phash",
"similarity_score": 100,
"group_size": 9856
},
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://com-ledger-desktop.pages.dev/",
"title": "Suspected Phishing | Cloudflare",
"submitted_at": "2026-09-02T14:46:02.710399",
"screenshot": "/api/v1/screenshot/123e4567-e89b-12d3-a456-426614174000.png",
"distance": 0,
"hash_match_type": "phash",
"similarity_score": 100,
"group_size": 9856
}
],
[
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://dizzy-emerald-dewkrsxti8-jtsodarm77.edgeone.app/",
"title": "EdgeOne Pages",
"submitted_at": "2026-05-24T15:17:25.420345",
"screenshot": "/api/v1/screenshot/123e4567-e89b-12d3-a456-426614174000.png",
"distance": 0,
"hash_match_type": "phash",
"similarity_score": 100,
"group_size": 7748
},
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://maa-status-gnudpl58lw.edgeone.dev/",
"title": "EdgeOne Pages",
"submitted_at": "2026-05-24T14:47:39.107760",
"screenshot": "/api/v1/screenshot/123e4567-e89b-12d3-a456-426614174000.png",
"distance": 0,
"hash_match_type": "phash",
"similarity_score": 100,
"group_size": 7748
}
]
],
"pagination": {
"page": 1,
"limit": 20,
"total_groups": 24179,
"total_pages": 1209,
"has_next": true,
"has_prev": false
},
"generated_at": "2026-09-02T18:26:11.351547+00:00",
"note": "Only exact hash matches (max_distance=0) supported. Use /api/v1/search/screenshot/phash/{hash} for fuzzy matching. Each group lists at most 10 of its members..."
}/api/v1/screenshot/statsScreenshot Statistics
Coverage statistics for perceptual screenshot hashing across public scans. The population is every public scan that has a screenshot in any of its capture columns, so screenshots_with_hashes and every entry in hash_types_distribution are subsets of total_screenshots.
Response
{
"total_screenshots": "integer",
"screenshots_with_hashes": "integer",
"hash_coverage_percent": "number",
"hash_types_distribution": {
"ahash": "integer",
"phash": "integer",
"dhash": "integer",
"whash": "integer",
"crop_resistant": "integer"
},
"recent_24h_hashes": "integer",
"generated_at": "string",
"supported_hash_types": [
"string"
]
}Example
Request
curl "https://scanmalware.com/api/v1/screenshot/stats"Response
{
"total_screenshots": 559358,
"screenshots_with_hashes": 521615,
"hash_coverage_percent": 93.25,
"hash_types_distribution": {
"ahash": 475279,
"phash": 475279,
"dhash": 475279,
"whash": 475279,
"crop_resistant": 475279
},
"recent_24h_hashes": 1657,
"generated_at": "2026-09-02T18:45:01.831260+00:00",
"supported_hash_types": [
"ahash - Average hash (basic similarity)",
"phash - Perceptual hash (robust to minor changes)"
]
}/api/v1/search/jarm/{jarm_signature}JARM Signature Search
Search for scans by JARM TLS fingerprint. JARM fingerprints are 62-character hashes that identify TLS server configurations.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
jarm_signature | string | Required | JARM TLS fingerprint (62-character hex string) |
page | integer | Optional | Page number |
limit | integer | Optional | Items per page |
Response
{
"jarm_signature": "string",
"total_results": "integer",
"results": [
{
"scan_id": "string",
"url": "string",
"final_url": "string",
"jarm_host": "string",
"jarm_port": "integer",
"jarm_url": "string",
"is_final_url": "boolean",
"title": "string",
"scan_type": "string",
"status": "string",
"submitted_at": "string",
"completed_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/search/jarm/29d3fd00029d29d21c42d43d00041df48f145f65c66577d0b01ecea881c1ba"Response
{
"jarm_signature": "29d3fd00029d29d21c42d43d00041df48f145f65c66577d0b01ecea881c1ba",
"total_results": 2,
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://google.com/",
"final_url": "https://www.google.com/",
"jarm_host": "www.google.com",
"jarm_port": 443,
"jarm_url": "https://www.google.com/",
"is_final_url": true,
"title": "Google",
"scan_type": "public",
"status": "completed",
"submitted_at": "2025-08-26T07:14:30.516606",
"completed_at": null
}
]
}/api/v1/jarm/scan/{scan_id}Get JARM Signatures for Scan
Get all JARM signatures associated with a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"signatures": [
{
"host": "string",
"port": "integer",
"jarm_signature": "string",
"url": "string",
"is_final_url": "boolean",
"is_known": "boolean",
"matched_domains": [
"string"
],
"created_at": "string"
}
],
"failed_hosts": [
{
"host": "string",
"port": "integer",
"status": "string",
"ip_address": "string",
"processing_time_ms": "integer",
"created_at": "string",
"failure_reason": "string",
"failure_details": "string",
"server_header": "null",
"detected_waf": "null",
"response_type": "string",
"detection_method": "null",
"cname_chain": "null",
"cert_issuer": "null",
"cert_sans": "null"
}
],
"analysis_summary": {
"total_attempts": "integer",
"successful": "integer",
"failed": "integer"
}
}Example
Request
curl "https://scanmalware.com/api/v1/jarm/scan/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"signatures": [
{
"host": "www.youtube.com",
"port": 443,
"jarm_signature": "27d40d40d29d40d1dc42d43d00041ded961c16c68658e95145597cf992c36c",
"url": "https://www.youtube.com/watch?v=jy4qYmf3TxA",
"is_final_url": true,
"is_known": false,
"matched_domains": [],
"created_at": "2026-09-02T10:35:57.668277"
},
{
"host": "1flex.org",
"port": 443,
"jarm_signature": "27d40d40d00040d1dc42d43d00041d6183ff1bfae51ebd88d70384363d525c",
"url": "https://1flex.org",
"is_final_url": false,
"is_known": false,
"matched_domains": [],
"created_at": "2026-09-02T10:35:57.542177"
}
],
"failed_hosts": [
{
"host": "1flex.org",
"port": 443,
"status": "failed",
"ip_address": "104.21.56.146",
"processing_time_ms": 16434,
"created_at": "2026-09-02T10:36:11.327853",
"failure_reason": "connection_reset",
"failure_details": "Server reset all connections during JARM probes.",
"server_header": null,
"detected_waf": null,
"response_type": "connection_reset",
"detection_method": null,
"cname_chain": null,
"cert_issuer": null,
"cert_sans": null
}
],
"analysis_summary": {
"total_attempts": 6,
"successful": 6,
"failed": 1
}
}/api/v1/jarm/statsJARM Statistics
Get statistics about JARM signatures in the database
Response
{
"statistics": {
"unique_signatures": "integer",
"total_scans": "integer",
"total_entries": "integer",
"unique_hosts": "integer"
},
"common_signatures": [
{
"jarm_signature": "string",
"scan_count": "integer",
"host_count": "integer",
"sample_hosts": [
"string"
]
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/jarm/stats"Response
{
"statistics": {
"unique_signatures": 4,
"total_scans": 16,
"total_entries": 26,
"unique_hosts": 5
},
"common_signatures": [
{
"jarm_signature": "29d3fd00029d29d21c42d43d00041df48f145f65c66577d0b01ecea881c1ba",
"scan_count": 10,
"host_count": 2,
"sample_hosts": ["google.com", "www.google.com"]
}
]
}/api/v1/search/similarSimilar Content Search
Find scans with similar content using fuzzy hashing
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Base scan ID to find similar scans for |
methods | array | Optional | Methods to use for similarity: screenshot, favicon, fuzzy |
page | integer | Optional | Page number |
limit | integer | Optional | Items per page |
Response
[
{
"scan_id": "string",
"url": "string",
"title": "string",
"similarity_score": "integer",
"tlsh_score": "integer | null",
"ssdeep_score": "integer | null",
"submitted_at": "string"
}
]Example
Request
curl "https://scanmalware.com/api/v1/search/similar?scan_id=123e4567-e89b-12d3-a456-426614174000&threshold=85"Response
[
{
"scan_id": "223e4567-e89b-12d3-a456-426614174001",
"url": "https://similar-site.com",
"title": "Similar Content Site",
"similarity_score": 92,
"tlsh_score": 15,
"ssdeep_score": 89,
"submitted_at": "2025-08-20T16:30:00.000Z"
}
]/api/v1/search/fuzzy/{hash_type}Search by Fuzzy Hash
Search for scans by fuzzy hash - TLSH, ssdeep, or sdhash (public scans only)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_type | string | Required | Fuzzy hash type: "tlsh", "ssdeep", or "sdhash" |
hash_value | string | Required | The fuzzy hash value to search for (query parameter) |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"hash_type": "string",
"hash_value": "string",
"count": "integer",
"results": [
{
"scan_id": "string",
"url": "string",
"title": "string",
"submitted_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/search/fuzzy/tlsh?hash_value=T1ABC123..."Response
{
"hash_type": "tlsh",
"hash_value": "T1ABC123...",
"count": 2,
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"title": "Example Domain",
"submitted_at": "2025-08-20T16:30:00.000Z"
}
]
}/api/v1/statsGet System Statistics
Retrieve system statistics and queue information
Response
{
"queue_length": "integer",
"running_scans": "integer",
"completed_24h": {
"public": "integer",
"unlisted": "integer",
"private": "integer"
}
}Example
Request
curl "https://scanmalware.com/api/v1/stats"Response
{
"queue_length": 5,
"running_scans": 2,
"completed_24h": {
"public": 150,
"unlisted": 25,
"private": 8
}
}/api/v1/screenshot/{scan_id}Get Scan Screenshot
Get scan screenshot with optional resizing and format conversion
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | |
width | integer | Optional | Resize width (maintains aspect ratio) |
height | integer | Optional | Resize height (maintains aspect ratio) |
format | string | Optional | Output format: png or webp |
Response
Binary image data — image/png by default, image/webp when ?format=webp.Example
Request
curl "https://scanmalware.com/api/v1/screenshot/123e4567-e89b-12d3-a456-426614174000?width=640&format=webp" -o screenshot.webpResponse
[Binary image data]/api/v1/healthHealth Check
Check system health and worker status
Response
{
"status": "string",
"service": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/health"Response
{
"status": "ok",
"service": "scanmalware-backend"
}/api/v1/ocr/{scan_id}Get OCR Text
Get OCR-extracted text from a scan's screenshot with language detection
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The scan ID to retrieve OCR text for |
Response
{
"scan_id": "string",
"ocr_text": "string",
"ocr_language": "string",
"confidence_score": "null",
"word_count": "integer",
"char_count": "integer",
"suspicious_regions": [
{
"bbox": {
"x": "integer",
"y": "integer",
"width": "integer",
"height": "integer"
},
"text": "string",
"pattern": "string",
"confidence": "integer"
}
],
"performed_at": "string",
"source": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/ocr/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"ocr_text": "Gundeazg cmd am (2)\n\nid Gm ‘Accesso all'informazione i Gestione rifiuti Tutti gli argomenti\"\nTRI fe\nIE HE\n. Lara = = = nia x\n\nrem\nne\n\n==;\n\n23 DICEMBRE 2025 2...",
"ocr_language": "ita",
"confidence_score": null,
"word_count": 132,
"char_count": 772,
"suspicious_regions": [],
"performed_at": "2026-01-04T01:15:19.361543",
"source": "database"
}/api/v1/search/ocrSearch OCR Text
Full-text search through OCR-extracted text from screenshots
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
q | string | Required | Search query (min 3 characters) |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"results": [
{
"scan_id": "string",
"url": "string",
"ocr_text_preview": "string",
"relevance_score": "float",
"scan_timestamp": "string"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/search/ocr?q=verify+human&page=1&limit=10"Response
{
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://suspicious-site.com",
"ocr_text_preview": "Please verify you are human by pressing Windows+R and typing...",
"relevance_score": 0.95,
"scan_timestamp": "2025-08-20T16:30:00.000Z"
}
],
"pagination": {
"page": 1,
"limit": 10,
"total": 3,
"pages": 1
}
}/api/v1/search/ocr/patternOCR Pattern Search
Search for specific patterns in OCR-extracted text
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
pattern | string | Required | Pattern to search for |
case_sensitive | boolean | Optional | Whether to perform case-sensitive search (default: false) |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"results": [
{
"scan_id": "string",
"url": "string",
"ocr_text_preview": "string",
"match_count": "integer",
"scan_timestamp": "string"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/search/ocr/pattern?pattern=Windows%2BR&case_sensitive=false"Response
{
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://suspicious-site.com",
"ocr_text_preview": "Press Windows+R to open Run dialog...",
"match_count": 3,
"scan_timestamp": "2025-08-20T16:30:00.000Z"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total": 5,
"pages": 1
}
}/api/v1/ocr/statsOCR Statistics
Get OCR processing statistics and language distribution
Response
{
"overall": {
"total_scans_with_ocr": "integer",
"avg_confidence": "integer",
"avg_word_count": "integer",
"avg_char_count": "integer",
"scans_with_suspicious_text": "integer"
},
"language_distribution": [
{
"language": "string",
"count": "integer"
}
],
"daily_stats": [
{
"date": "string",
"scans_with_ocr": "integer",
"avg_confidence": "integer",
"avg_word_count": "number",
"avg_processing_time_ms": "number",
"suspicious_count": "integer"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/ocr/stats"Response
{
"overall": {
"total_scans_with_ocr": 539708,
"avg_confidence": 0,
"avg_word_count": 54,
"avg_char_count": 309,
"scans_with_suspicious_text": 1163
},
"language_distribution": [
{
"language": "eng",
"count": 496909
},
{
"language": "ita",
"count": 20683
}
],
"daily_stats": [
{
"date": "2026-09-02",
"scans_with_ocr": 1405,
"avg_confidence": 0,
"avg_word_count": 61.39644128113879,
"avg_processing_time_ms": 1742.0946619217082,
"suspicious_count": 6
},
{
"date": "2026-09-01",
"scans_with_ocr": 1648,
"avg_confidence": 0,
"avg_word_count": 62.97997572815534,
"avg_processing_time_ms": 1667.513349514563,
"suspicious_count": 4
}
]
}/api/v1/clipboard/statsClipboard Statistics
Get global clipboard monitoring and pastejacking detection statistics
Response
{
"clipboard_events": {
"scans_with_clipboard": "integer",
"total_events": "integer",
"copy_events": "integer",
"paste_events": "integer",
"suspicious_events": "integer"
},
"pastejacking_detections": {
"scans_with_pastejacking": "integer",
"total_detections": "integer",
"critical": "integer",
"high": "integer",
"medium": "integer",
"low": "integer"
},
"daily_activity": "array"
}Example
Request
curl "https://scanmalware.com/api/v1/clipboard/stats"Response
{
"clipboard_events": {
"scans_with_clipboard": 142,
"total_events": 523,
"copy_events": 201,
"paste_events": 87,
"suspicious_events": 34
},
"pastejacking_detections": {
"scans_with_pastejacking": 28,
"total_detections": 45,
"critical": 5,
"high": 12,
"medium": 18,
"low": 10
},
"daily_activity": [
{
"date": "2025-08-20",
"scans_with_clipboard_activity": 15,
"total_events": 67,
"suspicious_events": 8,
"scans_with_pastejacking": 3
}
]
}/api/v1/clipboard/{scan_id}Get Clipboard Events
Get clipboard events captured during a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The scan ID to retrieve clipboard events for |
Response
{
"scan_id": "string",
"events": [
{
"event_type": "string",
"event_timestamp": "string",
"event_data": "object",
"page_url": "string",
"element_selector": "string",
"is_suspicious": "boolean",
"suspicious_reason": "string"
}
],
"statistics": "object",
"source": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/clipboard/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"events": [
{
"event_type": "copy",
"event_timestamp": "2025-08-20T16:30:15.000Z",
"event_data": {
"clipboardData": "powershell -Command iex",
"selection": "Run this command"
},
"page_url": "https://suspicious-site.com/verify",
"element_selector": "div.verification-steps",
"is_suspicious": true,
"suspicious_reason": "Contains potentially malicious command patterns"
}
],
"statistics": {
"total_events": 3,
"copy_events": 2,
"paste_events": 1,
"suspicious_events": 1
},
"source": "database"
}/api/v1/pastejacking/{scan_id}Get Pastejacking Detections
Get pastejacking attack detections for a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The scan ID to retrieve pastejacking detections for |
Response
{
"scan_id": "string",
"detections": [
{
"detection_type": "string",
"severity": "string",
"description": "string",
"technical_details": "object",
"affected_element": "string",
"mitigation_advice": "string",
"detected_at": "string"
}
],
"detection_count": "integer",
"max_severity": "string",
"source": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/pastejacking/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"detections": [
{
"detection_type": "hidden_payload",
"severity": "critical",
"description": "Hidden malicious content detected in DIV element",
"technical_details": {
"content": "powershell -NoProfile -ExecutionPolicy Bypass",
"tag": "DIV",
"visibility": "hidden",
"opacity": "0"
},
"affected_element": "div.hidden-command",
"mitigation_advice": "Avoid copying text from this page as it may contain hidden malicious content",
"detected_at": "2025-08-20T16:30:00.000Z"
},
{
"detection_type": "fake_modal",
"severity": "high",
"description": "Suspicious modal detected with pattern: /windows?\\s*\\+\\s*r/i",
"technical_details": {
"text": "Press Windows+R to verify",
"zIndex": "9999",
"position": "fixed"
},
"mitigation_advice": "Be cautious of verification prompts asking you to copy/paste commands",
"detected_at": "2025-08-20T16:30:00.000Z"
}
],
"detection_count": 2,
"max_severity": "critical",
"source": "database"
}/api/v1/search/clipboard/suspiciousSearch Suspicious Clipboard
Search for suspicious clipboard activity patterns across all scans
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
pattern | string | Optional | Pattern to search in suspicious clipboard events |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"results": [
{
"scan_id": "string",
"url": "string",
"event_count": "integer",
"suspicious_reason": "string",
"scan_timestamp": "string"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/search/clipboard/suspicious?pattern=powershell&page=1"Response
{
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://malicious-site.com",
"event_count": 5,
"suspicious_reason": "Contains potentially malicious command patterns",
"scan_timestamp": "2025-08-20T16:30:00.000Z"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total": 8,
"pages": 1
}
}/api/v1/technologies/searchSearch Technologies
Search for technologies by name or category with full-text search support
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
q | string | Optional | Search term for technology name (supports partial matching) |
category | string | Optional | Filter by category (e.g., "CMS", "Web Framework", "JavaScript Library") |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"results": [
{
"tech_name": "string",
"tech_category": "string",
"tech_version": "string | null",
"occurrence_count": "integer",
"last_detected": "string",
"avg_confidence": "integer"
}
],
"pagination": {
"page": "integer",
"limit": "integer",
"total_items": "integer",
"total_pages": "integer",
"has_next": "boolean",
"has_prev": "boolean"
},
"search_term": "null",
"category_filter": "null"
}Example
Request
curl "https://scanmalware.com/api/v1/technologies/search?q=wordpress&category=CMS"Response
{
"results": [
{
"tech_name": "HSTS",
"tech_category": "wappalyzer",
"tech_version": null,
"occurrence_count": 123383,
"last_detected": "2026-09-02T19:00:25.321342",
"avg_confidence": 40
},
{
"tech_name": "Cloudflare",
"tech_category": "wappalyzer",
"tech_version": null,
"occurrence_count": 122943,
"last_detected": "2026-09-02T19:00:13.583904",
"avg_confidence": 42.14440838437324
}
],
"pagination": {
"page": 1,
"limit": 50,
"total_items": 5018,
"total_pages": 101,
"has_next": true,
"has_prev": false
},
"search_term": null,
"category_filter": null
}/api/v1/technologies/popularPopular Technologies
Get the most frequently detected technologies
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
days | integer | Optional | Number of days to look back |
page | integer | Optional | Page number |
limit | integer | Optional | Items per page |
Response
{
"technologies": [
{
"tech_name": "string",
"tech_category": "string",
"scan_count": "integer",
"unique_versions": "integer",
"latest_version": "string | null"
}
],
"pagination": {
"page": "integer",
"limit": "integer",
"total_items": "integer",
"total_pages": "integer",
"has_next": "boolean",
"has_prev": "boolean"
},
"period_days": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/technologies/popular?time_period=7d&limit=5"Response
{
"technologies": [
{
"tech_name": "Cloudflare",
"tech_category": "wappalyzer",
"scan_count": 21307,
"unique_versions": 0,
"latest_version": null
},
{
"tech_name": "Cloudflare Bot Management",
"tech_category": "wappalyzer",
"scan_count": 19858,
"unique_versions": 0,
"latest_version": null
}
],
"pagination": {
"page": 1,
"limit": 20,
"total_items": 1287,
"total_pages": 65,
"has_next": true,
"has_prev": false
},
"period_days": 30
}/api/v1/technologies/combinations/{tech_name}Technology Combinations
Find technologies commonly used together with a specific technology
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
tech_name | string | Required | Technology name to find combinations for |
min_occurrences | integer | Optional | Minimum occurrences to include |
page | integer | Optional | Page number |
limit | integer | Optional | Items per page |
Response
{
"base_technology": "string",
"total_occurrences": "integer",
"combinations": [
{
"technology": "string",
"category": "string",
"co_occurrence_count": "integer",
"percentage": "number"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/technologies/combinations/WordPress"Response
{
"base_technology": "WordPress",
"total_occurrences": 45,
"combinations": [
{
"technology": "MySQL",
"category": "Database",
"co_occurrence_count": 42,
"percentage": 93.3
},
{
"technology": "PHP",
"category": "Programming Language",
"co_occurrence_count": 45,
"percentage": 100.0
}
],
"pagination": {
"page": 1,
"limit": 20,
"total_items": 25,
"total_pages": 2,
"has_next": true,
"has_prev": false
}
}/api/v1/technologies/statsTechnology Statistics
Get aggregated statistics about detected technologies
Response
{
"overall": {
"unique_technologies": "integer",
"total_scans": "integer",
"total_detections": "integer",
"categories": "integer"
},
"by_category": [
{
"category": "string",
"technology_count": "integer",
"scan_count": "integer"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/technologies/stats"Response
{
"overall": {
"unique_technologies": 2146,
"total_scans": 371602,
"total_detections": 2132086,
"categories": 11
},
"by_category": [
{
"category": "wappalyzer",
"technology_count": 2041,
"scan_count": 338404
},
{
"category": "miscellaneous",
"technology_count": 98,
"scan_count": 251855
}
]
}/api/v1/technologies/by-scan/{scan_id}Technologies by Scan
Get all technologies detected in a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"technologies": [
{
"name": "string",
"version": "string | null",
"category": "string",
"confidence": "integer",
"detected_at": "string",
"website": "null",
"description": "null",
"details": {
"cpe": "string | null",
"source": "string",
"implies": [
"string"
],
"detected_by": [
"string"
],
"detection_details": [
"object"
],
"confidence_breakdown": "object"
}
}
],
"source": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/technologies/by-scan/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"technologies": [
{
"name": "Bootstrap",
"version": "1787925560",
"category": "ui-framework",
"confidence": 100,
"detected_at": "2026-09-02T18:14:07.018606",
"website": null,
"description": null,
"details": []
},
{
"name": "Cloudflare",
"version": null,
"category": "wappalyzer",
"confidence": 40,
"detected_at": "2026-09-02T18:14:07.393850",
"website": null,
"description": null,
"details": {
"cpe": null,
"source": "wappalyzer",
"implies": [],
"detected_by": [
"headers"
],
"detection_details": [
{
"method": "headers",
"matches": [
{
"type": "presence",
"value": "DYNAMIC",
"header": "cf-cache-status"
},
{
"type": "presence",
"value": "a34e7b1ec971dbb7-FRA",
"header": "cf-ray"
}
]
}
],
"confidence_breakdown": {
"headers": 40
}
}
}
],
"source": "database"
}/api/v1/search/ip/{ip_address}Search by IP Address
Search for scans by IP address or partial IP (public scans only)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
ip_address | string | Required | IP address or partial IP to search for |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 50, max: 500) |
Response
{
"ip_address": "string",
"total_count": "integer",
"results": [
{
"scan_id": "string",
"url": "string",
"title": "string",
"submitted_at": "string",
"ip_addresses": [
"string"
],
"primary_ip": "string"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/search/ip/104.21.5.197"Response
{
"ip_address": "104.21.5.197",
"total_count": 3,
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"title": "Example Domain",
"submitted_at": "2025-08-20T16:30:00.000Z",
"ip_addresses": ["104.21.5.197", "172.67.182.169"],
"primary_ip": "104.21.5.197"
}
],
"pagination": {
"page": 1,
"limit": 50,
"total_items": 3,
"total_pages": 1,
"has_next": false,
"has_prev": false
}
}/api/v1/search/semanticAI-Powered Visual Search
Search for visually similar websites using natural language queries and CLIP embeddings
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
query | string | Required | Natural language search query (e.g., "login page", "shopping cart", "news website") |
threshold | float | Optional | Similarity threshold (-1.0 to 1.0, default: -0.3). Lower values return more results |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"results": [
{
"scan_id": "string",
"url": "string",
"title": "string",
"screenshot": "string",
"submitted_at": "string",
"scan_type": "string",
"similarity": "float",
"match_type": "string"
}
],
"total": "integer",
"page": "integer",
"limit": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/search/semantic?query=search+engine&threshold=-0.3&limit=5"Response
{
"results": [
{
"scan_id": "d0e3ae0a-e560-432a-af74-32777a6250f1",
"url": "https://google.com/",
"title": "Google",
"screenshot": "screenshots/d0e3ae0a-e560-432a-af74-32777a6250f1.png",
"submitted_at": "2025-08-31T10:30:00.000Z",
"scan_type": "public",
"similarity": -0.21,
"match_type": "visual"
},
{
"scan_id": "7d5a8b9c-1234-5678-90ab-cdef12345678",
"url": "https://www.baidu.com/",
"title": "百度一下,你就知道",
"screenshot": "screenshots/7d5a8b9c-1234-5678-90ab-cdef12345678.png",
"submitted_at": "2025-08-30T14:20:00.000Z",
"scan_type": "public",
"similarity": -0.22,
"match_type": "visual"
}
],
"total": 66,
"page": 1,
"limit": 5
}/api/v1/cpe/search/{cpe_pattern}Search CPE Records
Search for scans containing specific CPE patterns or technology names with pagination. Matches both full CPE strings and plain technology names (e.g. 'nginx', 'cowboy').
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
cpe_pattern | string | Required | CPE search pattern (e.g., "nginx", "apache:2.4", "gunicorn:19.9.0") |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Items per page (default: 20, max: 100) |
Response
{
"pattern": "string",
"results": [
{
"scan_id": "string",
"url": "string",
"final_url": "string",
"title": "string",
"status": "string",
"scan_type": "string",
"submitted_at": "string",
"cpe": "string",
"source": "string",
"detected_at": "string"
}
],
"pagination": {
"page": "integer",
"limit": "integer",
"total": "integer",
"pages": "integer"
}
}Example
Request
curl "https://scanmalware.com/api/v1/cpe/search/nginx:1.24"Response
{
"pattern": "nginx:1.24",
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"final_url": "https://example.com",
"title": "Example Site",
"status": "completed",
"scan_type": "public",
"submitted_at": "2025-09-01T10:00:00.000000",
"cpe": "cpe:2.3:a:nginx:nginx:1.24.0:*:*:*:*:*:*:*",
"source": "server_header",
"detected_at": "2025-09-01T10:00:30.000000+00:00"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total": 5,
"pages": 1
}
}/api/v1/cpe/statsCPE Statistics
Get global CPE detection statistics
Response
{
"total_scans_with_cpes": "integer",
"unique_cpes": "integer",
"total_detections": "integer",
"top_vendors": [
{
"vendor": "string",
"scan_count": "integer",
"detection_count": "integer"
}
],
"top_products": [
{
"vendor": "string",
"product": "string",
"scan_count": "integer",
"detection_count": "integer"
}
],
"detection_sources": [
{
"source": "string",
"count": "integer"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/cpe/stats"Response
{
"total_scans_with_cpes": 378172,
"unique_cpes": 1176,
"total_detections": 1340499,
"top_vendors": [
{
"vendor": "cloudflare",
"scan_count": 220421,
"detection_count": 220421
},
{
"vendor": "google",
"scan_count": 167891,
"detection_count": 297769
}
],
"top_products": [
{
"vendor": "cloudflare",
"product": "cloudflare",
"scan_count": 220421,
"detection_count": 220421
},
{
"vendor": "google",
"product": "google_frontend",
"scan_count": 144948,
"detection_count": 144948
}
],
"detection_sources": [
{
"source": "server_header",
"count": 913813
},
{
"source": "wappalyzer",
"count": 345544
}
]
}/api/v1/cpe/{scan_id}Get CPEs for Scan
Get all CPE records detected in a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The scan ID to get CPEs for |
Response
{
"scan_id": "string",
"cpes": [
{
"cpe": "string",
"vendor": "string",
"product": "string",
"version": "string",
"source": "string",
"detected_at": "string"
}
],
"total_count": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/cpe/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"cpes": [
{
"cpe": "cpe:2.3:a:nginx:nginx:1.24.0:*:*:*:*:*:*:*",
"vendor": "nginx",
"product": "nginx",
"version": "1.24.0",
"source": "server_header",
"detected_at": "2025-09-01T10:00:30.000000+00:00"
},
{
"cpe": "cpe:2.3:a:openssl:openssl:3.0.2:*:*:*:*:*:*:*",
"vendor": "openssl",
"product": "openssl",
"version": "3.0.2",
"source": "server_header",
"detected_at": "2025-09-01T10:00:30.000000+00:00"
}
],
"total_count": 2
}/api/v1/domain/stats/{domain}Domain Statistics
Get detailed statistics for a specific domain including scan history and threat analysis
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
domain | string | Required | The domain to get statistics for (e.g., "example.com") |
Response
{
"domain": "string",
"total_scans": "integer",
"first_seen": "string",
"last_seen": "string",
"scan_types": {
"public": "integer",
"unlisted": "integer",
"private": "integer"
},
"status_breakdown": {
"completed": "integer",
"failed": "integer",
"processing": "integer"
},
"risk_levels": {
"safe": "integer",
"low": "integer",
"medium": "integer",
"high": "integer",
"malicious": "integer"
}
}Example
Request
curl "https://scanmalware.com/api/v1/domain/stats/example.com"Response
{
"domain": "example.com",
"total_scans": 45,
"first_seen": "2025-01-15T10:00:00.000Z",
"last_seen": "2025-09-08T16:30:00.000Z",
"scan_types": {
"public": 40,
"unlisted": 4,
"private": 1
},
"status_breakdown": {
"completed": 42,
"failed": 2,
"processing": 1
},
"risk_levels": {
"safe": 38,
"low": 3,
"medium": 1,
"high": 0,
"malicious": 0
}
}/api/v1/domain/history/{domain}Domain Scan History
Get the complete scan history for a specific domain with detailed timeline
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
domain | string | Required | Domain name (e.g. example.com), or an IP address. |
page | integer | Optional | Page number |
limit | integer | Optional | Items per page |
Response
{
"domain": "string",
"history": [
{
"scan_id": "string",
"url": "string",
"submitted_at": "string",
"completed_at": "string",
"status": "string",
"scan_type": "string",
"risk_score": "integer",
"title": "string"
}
],
"total_count": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/domain/history/example.com?limit=10"Response
{
"domain": "example.com",
"history": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"submitted_at": "2025-09-08T16:30:00.000Z",
"completed_at": "2025-09-08T16:30:15.000Z",
"status": "completed",
"scan_type": "public",
"risk_score": 95,
"title": "Example Domain"
}
],
"total_count": 45
}/api/v1/ai/{scan_id}AI Security Analysis
Get AI-powered security analysis results for a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The scan ID to get AI analysis for |
Response
{
"scan_id": "string",
"results": {
"scan_id": "string",
"analysis": {
"verdict": "string",
"scam_type": "string",
"risk_score": "integer",
"_clamp_trace": {
"cls": "string",
"rank": "integer | null",
"risk": "integer",
"age_src": "string",
"age_days": "integer",
"floor_rule": "string | null",
"shared_host": "boolean",
"self_branded": "boolean",
"has_cred_form": "boolean",
"final_web_host": "boolean",
"strong_evidence": "boolean",
"suspicious_form": "boolean",
"asserts_evidence": "boolean",
"gambling_content": "boolean",
"suppression_rules": [
"string"
],
"cross_origin_exfil": "boolean",
"storefront_content": "boolean",
"content_gated_login": "boolean",
"control_panel_login": "boolean",
"form_action_xorigin": "boolean",
"redirect_brand_owner": "boolean",
"ranked_login_mislabel": "boolean",
"first_party_login_mislabel": "boolean"
},
"key_evidence": [
"string"
],
"risk_factors": [
"string"
],
"classification": "string",
"safety_factors": [
"string"
],
"recommended_action": "string",
"confidence_percentage": "integer",
"skipped_reason": "string",
"_floor_trace": {
"rule": "string",
"reason": "string",
"floored": "boolean",
"prev_score": "integer",
"floor_score": "integer",
"prev_verdict": "string",
"prev_classification": "string",
"dropped_safety_factors": [
"string"
],
"prev_recommended_action": "string"
}
},
"model_id": "string",
"analyzed_at": "number",
"prompt_length": "integer",
"prompt_version": "string"
},
"created_at": "string",
"updated_at": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/ai/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"results": {
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"analysis": {
"verdict": "This site is named as malicious in threat-intelligence feeds — rated high risk on that basis.",
"scam_type": "Not Applicable",
"risk_score": 7,
"_clamp_trace": {
"cls": "HIGH_RISK",
"rank": null,
"risk": 7,
"age_src": "rdap",
"age_days": 2409,
"floor_rule": "content_ioc",
"shared_host": true,
"self_branded": false,
"has_cred_form": false,
"final_web_host": true,
"strong_evidence": true,
"suspicious_form": true,
"asserts_evidence": true,
"gambling_content": false,
"suppression_rules": [],
"cross_origin_exfil": false,
"storefront_content": false,
"content_gated_login": false,
"control_panel_login": false,
"form_action_xorigin": false,
"redirect_brand_owner": false,
"ranked_login_mislabel": false,
"first_party_login_mislabel": false
},
"_floor_trace": {
"rule": "content_ioc",
"reason": "Threat-intel IoC names this site/content (malware-domain feed, not IP-reputation)",
"floored": true,
"prev_score": 3,
"floor_score": 7,
"prev_verdict": "Page shows no credential collection or malware, but unverified phishing reports and an unranked sub‑domain raise mild concern.",
"prev_classification": "LOW_RISK",
"dropped_safety_factors": [
"No forms collecting credentials or payment data",
"No malicious JavaScript or IDS alerts detected"
],
"prev_recommended_action": "Use with caution"
},
"key_evidence": [
"Two unverified single‑source threat‑intel matches labeling the domain as a wallet drainer (phishing)",
"No credential, login, or payment forms detected on the page"
],
"risk_factors": [
"Unverified threat‑intel match on primary domain",
"Unranked / unknown‑age sub‑domain on a shared hosting platform"
],
"classification": "HIGH_RISK",
"safety_factors": [],
"recommended_action": "Avoid interaction",
"confidence_percentage": 70
},
"model_id": "openai.gpt-oss-120b-1:0",
"analyzed_at": 1788357036.0431044,
"prompt_length": 24684,
"prompt_version": "d75bfecad43a"
},
"created_at": "2026-09-02T13:50:36.195054+00:00",
"updated_at": "2026-09-02T13:50:36.195054+00:00"
}/api/v1/ai/statsAI Analysis Statistics
Get global statistics for AI-powered security analysis
Response
{
"total_analyses": "integer",
"recent_analyses_7d": "integer",
"classifications": [
{
"name": "string",
"count": "integer"
}
],
"scam_types": [
{
"name": "string",
"count": "integer"
}
],
"risk_distribution": [
{
"level": "string",
"count": "integer"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/ai/stats"Response
{
"total_analyses": 513190,
"recent_analyses_7d": 12047,
"classifications": [
{
"name": "LEGITIMATE",
"count": 342604
},
{
"name": "LOW_RISK",
"count": 81754
}
],
"scam_types": [
{
"name": "Credential Phishing",
"count": 18545
},
{
"name": "Phishing",
"count": 18084
}
],
"risk_distribution": [
{
"level": "Very Low (0-1)",
"count": 339372
},
{
"level": "Low (2-3)",
"count": 84544
}
]
}/api/v1/ai/search/classificationSearch by AI Classification
Search for scans by AI classification type
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
classification | string | Required | Classification type: LEGITIMATE, LOW_RISK, MODERATE_RISK, HIGH_RISK, CONFIRMED_SCAM, or NOT_ASSESSED (the scanner never reached the site, so no assessment was possible — this is not a statement that the site is safe) |
limit | integer | Optional | Maximum results (1-1000, default: 100) |
Response
{
"results": [
{
"scan_id": "string",
"url": "string",
"classification": "string",
"confidence": "number",
"risk_level": "string",
"submitted_at": "string"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/ai/search/classification?classification=HIGH_RISK&limit=10"Response
{
"results": [
{
"scan_id": "abc123de-f456-7890-abcd-ef1234567890",
"url": "https://suspicious-site.com",
"classification": "phishing",
"confidence": 0.92,
"risk_level": "high",
"submitted_at": "2025-09-08T14:00:00.000Z"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total": 65,
"pages": 4
}
}/api/v1/ai/search/high-riskSearch High-Risk AI Detections
Find public scans whose AI security assessment is both high-risk and high-confidence. Scale caveat: min_risk_score here is on the AI engine's 0-10 scale. The rule-engine equivalent, /api/v1/analyzers/search/high-risk, takes 0-100 for a parameter of the same name — the two are not interchangeable. min_confidence is a 0-100 percentage on this endpoint. Returns a flat list capped by limit; this endpoint is not paginated.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
min_risk_score | integer | Optional | Minimum AI risk score, on a 0-10 scale (analysis.risk_score). NOTE: /api/v1/analyzers/search/high-risk takes a min_risk_score on a 0-100 scale instead -- the two engines score on different scales and the parameter is not interchangeable. |
min_confidence | integer | Optional | Minimum AI confidence, as a 0-100 percentage (analysis.confidence_percentage). Unlike min_risk_score this one really is a percentage, so 70 means 70%. |
limit | integer | Optional | Maximum results |
Response
{
"filters": {
"min_risk_score": "integer",
"min_confidence": "integer"
},
"count": "integer",
"results": [
{
"scan_id": "string",
"url": "string",
"title": "string",
"submitted_at": "string",
"analysis": {
"verdict": "string",
"scam_type": "string",
"risk_score": "integer",
"classification": "string",
"confidence_percentage": "integer",
"key_evidence": [
"string"
],
"risk_factors": [
"string"
],
"safety_factors": [
"string"
],
"recommended_action": "string"
},
"analyzed_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/ai/search/high-risk?min_risk_score=9&min_confidence=90&limit=1"Response
{
"filters": {
"min_risk_score": 9,
"min_confidence": 90
},
"count": 1,
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://login.example-lookalike.test/account",
"title": "Sign in to your account",
"submitted_at": "2026-08-27T18:22:41.900312",
"analysis": {
"verdict": "This page reproduces a well-known brand's sign-in flow on an unrelated domain.",
"scam_type": "credential_phishing",
"risk_score": 9,
"classification": "malicious",
"confidence_percentage": 95,
"key_evidence": [
"Password field posts to an unrelated origin",
"Brand logo served from a look-alike domain"
],
"risk_factors": [
"Domain registered 3 days ago"
],
"safety_factors": [],
"recommended_action": "block"
},
"analyzed_at": "2026-08-27T18:24:06.551204"
}
]
}/api/v1/ai/search/scam-typeSearch by Scam Type
Search for scans by specific scam type detected by AI
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scam_type | string | Required | Scam type to search for (e.g., "tech_support", "fake_shopping", "crypto_scam") |
limit | integer | Optional | Maximum results (1-1000, default: 100) |
Response
{
"scam_type": "string",
"results": [
{
"scan_id": "string",
"url": "string",
"scam_type": "string",
"confidence": "number",
"description": "string",
"submitted_at": "string"
}
],
"pagination": "object"
}Example
Request
curl "https://scanmalware.com/api/v1/ai/search/scam-type?scam_type=tech_support"Response
{
"scam_type": "tech_support",
"results": [
{
"scan_id": "def456gh-ijkl-7890-mnop-qrs123456789",
"url": "https://fake-microsoft-support.com",
"scam_type": "tech_support",
"confidence": 0.94,
"description": "Fake Microsoft tech support scam with phone number",
"submitted_at": "2025-09-08T12:00:00.000Z"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total": 15,
"pages": 1
}
}/api/v1/safe-browsing/{scan_id}Google Safe Browsing Results
Get Google Safe Browsing threat detection results for a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The scan ID to get Safe Browsing results for |
Response
{
"scan_id": "string",
"threats": [
{
"threat_type": "string",
"platform_type": "string",
"cache_duration": "string",
"detected_at": "string",
"raw_response": {
"threat": "object",
"threatType": "string",
"platformType": "string",
"cacheDuration": "string",
"threatEntryType": "string"
}
}
],
"has_threats": "boolean",
"total_threats": "integer - only present when has_threats is true"
}Example
Request
curl "https://scanmalware.com/api/v1/safe-browsing/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"threats": [
{
"threat_type": "SOCIAL_ENGINEERING",
"platform_type": "ANY_PLATFORM",
"cache_duration": "300s",
"detected_at": "2025-10-10T07:32:05.060695Z",
"raw_response": {
"threat": {
"url": "https://arabacioglugrup.com//plala.or.jp/Sites//index.html"
},
"threatType": "SOCIAL_ENGINEERING",
"platformType": "ANY_PLATFORM",
"cacheDuration": "300s",
"threatEntryType": "URL"
}
},
{
"threat_type": "SOCIAL_ENGINEERING",
"platform_type": "ANY_PLATFORM",
"cache_duration": "300s",
"detected_at": "2025-10-10T07:32:05.060695Z",
"raw_response": {
"threat": {
"url": "https://arabacioglugrup.com//plala.or.jp/Sites//index.html"
},
"threatType": "SOCIAL_ENGINEERING",
"platformType": "ANY_PLATFORM",
"cacheDuration": "300s",
"threatEntryType": "URL"
}
}
],
"has_threats": true,
"total_threats": 3
}/api/v1/safe-browsing/statsSafe Browsing Statistics
Get global Google Safe Browsing detection statistics
Response
{
"total_threats": "integer",
"recent_threats_7d": "integer",
"scans_with_threats": "integer",
"threat_types": [
{
"type": "string",
"count": "integer"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/safe-browsing/stats"Response
{
"total_threats": 6431,
"recent_threats_7d": 257,
"scans_with_threats": 5821,
"threat_types": [
{
"type": "SOCIAL_ENGINEERING",
"count": 6339
},
{
"type": "UNWANTED_SOFTWARE",
"count": 75
}
]
}/api/v1/rdap/{scan_id}RDAP/WHOIS Information
Get RDAP/WHOIS domain registration information for a scan Returns domain age, registration date, and other RDAP data with proper security validation. Args: scan_id: UUID of the scan Returns: RDAPResponse: Domain registration information Raises: HTTPException: If scan_id is invalid or scan not found
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"domain": "string",
"rdap_query_timestamp": "string",
"registration_date": "string",
"expiration_date": "string",
"domain_age": {
"days": null,
"category": null,
"risk_level": null,
"risk_score": null
},
"registrar": "string",
"nameservers": [
"string"
],
"status": [
"string"
],
"data_source": "string",
"ip_rdap_data": [
"object"
],
"error": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/rdap/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"domain": "pages.dev",
"rdap_query_timestamp": "2026-09-02T18:53:51.584328+00:00",
"registration_date": "2020-09-02T02:33:29.228000+00:00",
"expiration_date": "2027-09-02T02:33:29.228000+00:00",
"domain_age": {
"days": 2191,
"category": "WELL_ESTABLISHED",
"risk_level": "low",
"risk_score": 0.8
},
"registrar": null,
"nameservers": [
"adi.ns.cloudflare.com",
"karl.ns.cloudflare.com"
],
"status": [
"client delete prohibited",
"client transfer prohibited"
],
"data_source": "rdap",
"ip_rdap_data": [
{
"ip_address": "192.178.183.94/32",
"handle": "NET-192-178-0-0-1",
"parent_handle": "NET-192-0-0-0-0",
"name": "GOOGLE",
"whois_server": "whois.arin.net",
"type": "ip network",
"description": [],
"registration_date": "2012-07-12T22:01:22+00:00",
"last_changed_date": "2012-07-12T22:01:22+00:00",
"rdap_url": "https://rdap.arin.net/registry/ip/192.178.0.0",
"rir": "arin",
"country": "",
"ip_version": 4,
"assignment_type": "direct allocation",
"network": "192.178.0.0/15",
"entities": {
"abuse": [
{
"rir": "arin",
"tel": "+1-650-253-0000",
"url": "https://rdap.arin.net/registry/entity/ABUSE5250-ARIN",
"name": "Google Inc.",
"type": "entity",
"email": "[email protected]",
"handle": "ABUSE5250-ARIN",
"address": {
"po_box": "",
"region": "",
"country": "",
"locality": "",
"ext_address": "",
"postal_code": "",
"street_address": ""
},
"whois_server": "whois.arin.net"
}
],
"technical": [
{
"rir": "arin",
"tel": "+1-650-253-0000",
"url": "https://rdap.arin.net/registry/entity/ZG39-ARIN",
"name": "Google LLC",
"type": "entity",
"email": "[email protected]",
"handle": "ZG39-ARIN",
"address": {
"po_box": "",
"region": "",
"country": "",
"locality": "",
"ext_address": "",
"postal_code": "",
"street_address": ""
},
"whois_server": "whois.arin.net"
}
],
"registrant": [
{
"rir": "arin",
"url": "https://rdap.arin.net/registry/entity/GOGL",
"name": "Google LLC",
"type": "entity",
"handle": "GOGL",
"address": {
"po_box": "",
"region": "",
"country": "",
"locality": "",
"ext_address": "",
"postal_code": "",
"street_address": ""
},
"whois_server": "whois.arin.net"
}
],
"administrative": [
{
"rir": "arin",
"tel": "+1-650-253-0000",
"url": "https://rdap.arin.net/registry/entity/ZG39-ARIN",
"name": "Google LLC",
"type": "entity",
"email": "[email protected]",
"handle": "ZG39-ARIN",
"address": {
"po_box": "",
"region": "",
"country": "",
"locality": "",
"ext_address": "",
"postal_code": "",
"street_address": ""
},
"whois_server": "whois.arin.net"
}
]
},
"lookup_timestamp": "2026-09-02T18:18:46.260444+00:00"
},
{
"ip_address": "192.178.183.94/32",
"handle": "NET-192-178-0-0-1",
"parent_handle": "NET-192-0-0-0-0",
"name": "GOOGLE",
"whois_server": "whois.arin.net",
"type": "ip network",
"description": [],
"registration_date": "2012-07-12T22:01:22+00:00",
"last_changed_date": "2012-07-12T22:01:22+00:00",
"rdap_url": "https://rdap.arin.net/registry/ip/192.178.0.0",
"rir": "arin",
"country": "",
"ip_version": 4,
"assignment_type": "direct allocation",
"network": "192.178.0.0/15",
"entities": {
"abuse": [
{
"rir": "arin",
"tel": "+1-650-253-0000",
"url": "https://rdap.arin.net/registry/entity/ABUSE5250-ARIN",
"name": "Google Inc.",
"type": "entity",
"email": "[email protected]",
"handle": "ABUSE5250-ARIN",
"address": {
"po_box": "",
"region": "",
"country": "",
"locality": "",
"ext_address": "",
"postal_code": "",
"street_address": ""
},
"whois_server": "whois.arin.net"
}
],
"technical": [
{
"rir": "arin",
"tel": "+1-650-253-0000",
"url": "https://rdap.arin.net/registry/entity/ZG39-ARIN",
"name": "Google LLC",
"type": "entity",
"email": "[email protected]",
"handle": "ZG39-ARIN",
"address": {
"po_box": "",
"region": "",
"country": "",
"locality": "",
"ext_address": "",
"postal_code": "",
"street_address": ""
},
"whois_server": "whois.arin.net"
}
],
"registrant": [
{
"rir": "arin",
"url": "https://rdap.arin.net/registry/entity/GOGL",
"name": "Google LLC",
"type": "entity",
"handle": "GOGL",
"address": {
"po_box": "",
"region": "",
"country": "",
"locality": "",
"ext_address": "",
"postal_code": "",
"street_address": ""
},
"whois_server": "whois.arin.net"
}
],
"administrative": [
{
"rir": "arin",
"tel": "+1-650-253-0000",
"url": "https://rdap.arin.net/registry/entity/ZG39-ARIN",
"name": "Google LLC",
"type": "entity",
"email": "[email protected]",
"handle": "ZG39-ARIN",
"address": {
"po_box": "",
"region": "",
"country": "",
"locality": "",
"ext_address": "",
"postal_code": "",
"street_address": ""
},
"whois_server": "whois.arin.net"
}
]
},
"lookup_timestamp": "2026-09-02T18:18:41.660897+00:00"
}
],
"error": null
}/api/v1/tls/{scan_id}TLS Certificate Analysis
Full TLS/SSL certificate analysis for a scan: chain validation, expiry, key and signature algorithms, CAA records and a risk score. The sans block lists the certificate's Subject Alternative Names — the only place wildcard hostnames such as *.cloud.example.com appear, since a wildcard never resolves and so cannot show up in DNS-derived data. See the “Finding subdomains” guide at /api-docs#finding-subdomains for how this compares with the other sources.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"subject_common_name": "string",
"subject_organization": "string",
"subject_organizational_unit": "string",
"subject_country": "string",
"subject_state": "string",
"subject_locality": "string",
"issuer_common_name": "string",
"issuer_organization": "string",
"issuer_country": "string",
"not_before": "string",
"not_after": "string",
"is_valid": "boolean",
"is_expired": "boolean",
"is_not_yet_valid": "boolean",
"days_until_expiry": "integer",
"validity_period_days": "integer",
"serial_number": "string",
"signature_algorithm": "string",
"key_algorithm": "string",
"key_size": "integer",
"version": "integer",
"fingerprint_sha1": "string",
"fingerprint_sha256": "string",
"fingerprint_md5": "string",
"ja4x": "string",
"ja4x_certificate_count": "integer",
"rsa_modulus_hash": "string",
"rsa_modulus_size": "integer",
"rsa_public_exponent": "integer",
"rsa_key_analysis": "object",
"is_debian_weak_key": "boolean",
"is_roca_vulnerable": "boolean",
"has_common_modulus": "boolean",
"key_entropy_score": "number",
"is_self_signed": "boolean",
"is_wildcard": "boolean",
"is_ev_cert": "boolean",
"is_lets_encrypt": "boolean",
"certificate_pem": "string",
"sans": "object",
"extensions": "object",
"chain": "object",
"chain_valid": "boolean",
"chain_validation": "object",
"hostname_match": "boolean",
"security_analysis": "object",
"risk_score": "integer",
"risk_factors": "object",
"is_in_ct_logs": "boolean",
"ct_log_entries": "object",
"ct_first_seen": "string",
"ct_last_seen": "string",
"ct_log_sources": [
"string"
],
"ct_certificate_history": "object",
"ct_related_domains": "object",
"ct_ip_history": "object",
"ct_certificate_count": "integer",
"ct_days_since_first_cert": "integer",
"cert_recently_issued": "boolean",
"cert_recently_changed": "boolean",
"shared_with_domains": "integer",
"has_caa_records": "boolean",
"caa_records": [
"object"
],
"caa_authorized_cas": [
null
],
"caa_compliant": "boolean",
"caa_validation_data": "object",
"revocation_checked": "boolean",
"is_revoked": "boolean",
"processing_time_ms": "integer",
"error_message": "string",
"created_at": "string",
"updated_at": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/tls/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"subject_common_name": "*.google.com",
"subject_organization": null,
"subject_organizational_unit": null,
"subject_country": null,
"subject_state": null,
"subject_locality": null,
"issuer_common_name": "WE2",
"issuer_organization": "Google Trust Services",
"issuer_country": "US",
"not_before": "2026-08-10T08:37:42+00:00",
"not_after": "2026-11-02T08:37:41+00:00",
"is_valid": true,
"is_expired": false,
"is_not_yet_valid": false,
"days_until_expiry": 60,
"validity_period_days": 83,
"serial_number": "22278298368170369558076281217401292819",
"signature_algorithm": "ecdsa-with-SHA256",
"key_algorithm": "ECDSA",
"key_size": 256,
"version": 2,
"fingerprint_sha1": "cb38342f7d9e359325097cbccfd58bcd34cd70e7",
"fingerprint_sha256": "50170301aac0db75430ba6dc1f27c3aa1e932f67a78c547dfe7b6ae6f19fc7ff",
"fingerprint_md5": "f28c43c46b19d97fe992c8d082967e74",
"rsa_modulus_hash": null,
"rsa_modulus_size": null,
"rsa_public_exponent": null,
"rsa_key_analysis": null,
"is_debian_weak_key": false,
"is_roca_vulnerable": false,
"has_common_modulus": false,
"key_entropy_score": null,
"is_self_signed": false,
"is_wildcard": true,
"is_ev_cert": false,
"is_lets_encrypt": false,
"certificate_pem": "-----BEGIN CERTIFICATE-----\nMIIHkTCCBzagAwIBAgIQEMKk6eFGSH0KMp9unNUIEzAKBggqhkjOPQQDAjA7MQsw\nCQYDVQQGEwJVUzEeMBwGA1UEChMVR29vZ2xlIFRydXN0IFNlcnZpY2VzMQwwCgYD...",
"sans": {
"dns_names": [
"*.google.com",
"*.appengine.google.com"
],
"wildcards": [
"*.google.com",
"*.appengine.google.com"
],
"risk_score": 20,
"total_sans": 65,
"other_types": [],
"ip_addresses": [],
"risk_factors": [
{
"factor": "Wildcard certificate",
"severity": "low",
"description": "Certificate covers *.google.com, *.appengine.google.com, *.bdn.dev, *.origin-test.bdn.dev, *.cloud.google.com, *.crowdsource.google.com, *.datacompute.google..."
},
{
"factor": "Excessive unrelated domains",
"severity": "medium",
"description": "Certificate covers 55 unrelated domains"
}
],
"is_multi_domain": true,
"related_domains": [
"*.google.com",
"*.appengine.google.com"
],
"is_wildcard_cert": true,
"unrelated_domains": [
"*.bdn.dev",
"*.origin-test.bdn.dev"
],
"unique_base_domains": [
"goo.gl",
"googlecommerce.com"
]
},
"extensions": null,
"chain": null,
"chain_valid": null,
"chain_validation": {
"issues": [],
"is_ca_cert": false,
"is_trusted": true,
"is_self_signed": false,
"has_authority_key_id": true,
"chain_length_estimate": 2
},
"hostname_match": true,
"security_analysis": {
"findings": [
{
"issue": "CAA policy violation",
"severity": "critical",
"description": "Certificate issued by 'WE2' but domain CAA policy only authorizes: pki.goog"
}
],
"risk_score": 0
},
"risk_score": 45,
"risk_factors": null,
"is_in_ct_logs": true,
"ct_log_entries": [
{
"log": "x",
"hash": "cb38342f7d9e359325097cbccfd58bcd34cd70e7",
"timestamp": 1788170703440
},
{
"log": "x",
"hash": "cb38342f7d9e359325097cbccfd58bcd34cd70e7",
"timestamp": 1788170703440
}
],
"ct_first_seen": "2026-07-07T20:23:23.492000+00:00",
"ct_last_seen": "2026-08-31T10:05:03.440000+00:00",
"ct_log_sources": null,
"ct_certificate_history": null,
"ct_related_domains": null,
"ct_ip_history": null,
"ct_certificate_count": 100,
"ct_days_since_first_cert": null,
"cert_recently_issued": true,
"cert_recently_changed": false,
"shared_with_domains": 0,
"has_caa_records": true,
"caa_records": [
{
"tag": "issue",
"flags": 0,
"value": "pki.goog"
}
],
"caa_authorized_cas": [
"pki.goog"
],
"caa_compliant": false,
"caa_validation_data": {
"issues": [
{
"issue": "CAA policy violation",
"severity": "critical",
"description": "Certificate issued by 'WE2' but domain CAA policy only authorizes: pki.goog"
}
],
"is_compliant": false,
"has_caa_policy": true,
"issuer_authorized": false
},
"revocation_checked": false,
"is_revoked": null,
"processing_time_ms": 314,
"error_message": null,
"created_at": "2026-09-02T17:58:40.359791+00:00",
"updated_at": "2026-09-02T17:58:40.359791+00:00"
}/api/v1/tls/{scan_id}/asn1TLS Certificate ASN.1 Structure
Get the raw ASN.1 (Abstract Syntax Notation One) structure of the TLS/SSL certificate. Returns detailed parsed structure and human-readable dump of all certificate fields, extensions, and encoded values.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"asn1_structure": {
"version": "string",
"serial_number": "string",
"signature_algorithm": {
"algorithm": "string (OID)",
"parameters": "string | null"
},
"issuer": "object",
"validity": {
"not_before": "string (ISO 8601)",
"not_after": "string (ISO 8601)"
},
"subject": "object",
"subject_public_key_info": {
"algorithm": "string (OID)",
"parameters": "string | null",
"public_key_size": "integer"
},
"extensions": "array of objects",
"signature_value_size": "integer"
},
"raw_asn1_dump": "string (formatted text)"
}Example
Request
curl "https://scanmalware.com/api/v1/tls/123e4567-e89b-12d3-a456-426614174000/asn1"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"asn1_structure": {
"version": "v3",
"serial_number": "227830333772454795620750445496253172213",
"signature_algorithm": {
"algorithm": "1.2.840.10045.4.3.2",
"parameters": null
},
"issuer": {
"country": "GB",
"organization": "Sectigo Limited",
"common_name": "Sectigo ECC Domain Validation Secure Server CA"
},
"validity": {
"not_before": "2025-02-05T00:00:00+00:00",
"not_after": "2026-02-05T23:59:59+00:00"
},
"subject": {
"common_name": "example.com"
},
"subject_public_key_info": {
"algorithm": "1.2.840.10045.2.1",
"parameters": null,
"public_key_size": 520
},
"extensions": [
{
"extn_id": "2.5.29.17",
"extn_name": "2.5.29.17",
"critical": false,
"extn_value": ["example.com", "www.example.com"]
}
],
"signature_value_size": 560
},
"raw_asn1_dump": "Certificate:\n Version: v3\n Serial Number: 227830333772454795620750445496253172213\n ..."
}/api/v1/malware/{scan_id}Malware Detection Results
Antivirus detections for one scan. Only resources where a threat was found are returned, so a clean scan yields an empty threats array rather than a 404. threat_count deduplicates by (threat_name, url); total_detections is the raw row count, which is higher when the same resource was scanned more than once.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"threats": [
{
"url": "string",
"content_hash": "string",
"content_type": "string",
"content_size": "integer",
"threat_detected": "boolean",
"threat_name": "string",
"scan_time": "number",
"scanned_at": "string",
"error": "string"
}
],
"threat_count": "integer",
"total_detections": "integer",
"source": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/malware/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"threats": [
{
"url": "https://example.com/assets/file/download.php",
"content_hash": "ca3b43878eb978ced36bd215debd58b00ed2a7087c51e77c84c92b71ccac3fca",
"content_type": "application/octet-stream",
"content_size": 3353,
"threat_detected": true,
"threat_name": "Win.Trojan.Suspect-34",
"scan_time": 0.003717,
"scanned_at": "2026-08-12T00:49:44.503965",
"error": null
}
],
"threat_count": 1,
"total_detections": 2,
"source": "database"
}/api/v1/malware/threats/recentRecent Malware Threats
Malware detections across all scans within a recent time window (hours, 1-168). threats is the flat list; threat_groups is the same rows keyed by threat name, so unique_threats is the number of distinct names. Detections are rare — an empty result for a 24-hour window is normal.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hours | integer | Optional | Hours to look back |
limit | integer | Optional | Maximum results |
Response
{
"time_range_hours": "integer",
"total_threats": "integer",
"unique_threats": "integer",
"threats": [
{
"scan_id": "string",
"url": "string",
"threat_name": "string",
"content_type": "string",
"content_size": "integer",
"scanned_at": "string"
}
],
"threat_groups": {
"<threat_name>": [
{
"scan_id": "string",
"url": "string",
"threat_name": "string",
"content_type": "string",
"content_size": "integer",
"scanned_at": "string"
}
]
}
}Example
Request
curl "https://scanmalware.com/api/v1/malware/threats/recent?hours=168&limit=5"Response
{
"time_range_hours": 168,
"total_threats": 1,
"unique_threats": 1,
"threats": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com/assets/file/download.php",
"threat_name": "Win.Trojan.Suspect-34",
"content_type": "application/octet-stream",
"content_size": 3353,
"scanned_at": "2026-08-12T00:49:44.503965"
}
],
"threat_groups": {
"Win.Trojan.Suspect-34": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com/assets/file/download.php",
"threat_name": "Win.Trojan.Suspect-34",
"content_type": "application/octet-stream",
"content_size": 3353,
"scanned_at": "2026-08-12T00:49:44.503965"
}
]
}
}/api/v1/malware/statsMalware Detection Statistics
Platform-wide antivirus scanning statistics. overall covers all time; recent_24h and hourly_trends cover the last 24 hours. A "resource" is one fetched sub-resource (script, image, document), so total_scans counts resource scans rather than page scans — unique_scans is the page count and unique_resources the number of distinct content hashes. avg_scan_time and max_scan_time are elapsed seconds. Resources scanned before 2026-08-28 via the proxy path recorded no usable duration and are null, so these two aggregates are computed over the subset of rows that carry one. Every other field is computed over all rows.
Response
{
"overall": {
"total_scans": "integer",
"total_threats": "integer",
"avg_scan_time": "number",
"max_scan_time": "number",
"total_bytes_scanned": "integer",
"unique_scans": "integer",
"unique_resources": "integer",
"unique_threat_types": "integer"
},
"recent_24h": {
"resources_scanned_24h": "integer",
"threats_detected_24h": "integer",
"active_scans_24h": "integer"
},
"top_threats": [
{
"threat_name": "string",
"detection_count": "integer",
"affected_scans": "integer"
}
],
"hourly_trends": [
{
"hour": "string",
"resources_scanned": "integer",
"threats_detected": "integer"
}
],
"timestamp": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/malware/stats"Response
{
"overall": {
"total_scans": 18723153,
"total_threats": 1210,
"avg_scan_time": 0.016259437193814275,
"max_scan_time": 80.585406,
"total_bytes_scanned": 616056276070,
"unique_scans": 483732,
"unique_resources": 4107912,
"unique_threat_types": 22
},
"recent_24h": {
"resources_scanned_24h": 80660,
"threats_detected_24h": 0,
"active_scans_24h": 1626
},
"top_threats": [
{
"threat_name": "Win.Trojan.Crypt-291",
"detection_count": 1047,
"affected_scans": 6
}
],
"hourly_trends": [
{
"hour": "2026-08-28T09:00:00",
"resources_scanned": 3612,
"threats_detected": 0
}
],
"timestamp": "2026-08-28T11:58:14.203981"
}/api/v1/reports/{scan_id}Get Scan Reports
Retrieve user-submitted reports for a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
report_type | string | Optional | Filter by report type (safe, phishing, malware, etc.) |
Response
{
"scan_id": "string",
"reports": [
{
"id": "integer",
"report_type": "string",
"report_details": "string",
"created_at": "string",
"status": "string"
}
],
"total": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/reports/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"reports": [
{
"id": 956,
"report_type": "malware",
"report_details": "User marked this website as malicious",
"created_at": "2026-09-02T13:45:26.308577",
"status": "pending"
}
],
"total": 1
}/api/v1/analyzers/{scan_id}Get Analyzer Results
Get security analyzer results for a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"risk_score": "integer",
"classification": "string",
"verdict": "string",
"risk_factors": "array",
"safety_factors": "array",
"confidence_percentage": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/analyzers/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"risk_score": 85,
"classification": "MALICIOUS",
"verdict": "High risk phishing site detected",
"risk_factors": [
"Suspicious login form",
"Recently registered domain",
"Known phishing kit detected"
],
"safety_factors": [],
"confidence_percentage": 92
}/api/v1/analyzers/search/high-riskSearch High-Risk Scans
Find public scans with a high rule-engine security score, ordered by score descending. Scale caveat: min_risk_score here is on the rule engine's 0-100 scale. The AI equivalent, /api/v1/ai/search/high-risk, takes 0-10 for a parameter of the same name — the two are not interchangeable. Pagination fields are returned at the top level, not nested under a pagination object.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
min_risk_score | integer | Optional | Minimum rule-engine risk score, on a 0-100 scale (security_verdict.overall_score). NOTE: /api/v1/ai/search/high-risk takes a min_risk_score on a 0-10 scale instead -- the two engines score on different scales and the parameter is not interchangeable. |
page | integer | Optional | Page number |
limit | integer | Optional | Items per page |
Response
{
"results": [
{
"scan_id": "string",
"url": "string",
"risk_score": "integer",
"verdict": "string",
"confidence": "integer",
"analyzed_at": "string"
}
],
"total": "integer",
"page": "integer",
"limit": "integer",
"total_pages": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/analyzers/search/high-risk?min_risk_score=90&limit=1"Response
{
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://login.example-lookalike.test/account",
"risk_score": 95,
"verdict": "malicious",
"confidence": 90,
"analyzed_at": "2026-08-27T18:23:11.048772"
}
],
"total": 4713,
"page": 1,
"limit": 1,
"total_pages": 4713
}/api/v1/analyzers/stats/overviewAnalyzer Statistics Overview
Get overall statistics from security analyzers
Response
{
"analyzers": [],
"total_analyzers": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/analyzers/stats/overview"Response
{
"analyzers": [],
"total_analyzers": 0
}/api/v1/ioc/{scan_id}IoC Threat Intelligence
Get IoC (Indicators of Compromise) threat intelligence matches for a scan Returns all matched malicious indicators (IPs and domains) that were found in the threat intelligence database. Args: scan_id: UUID of the scan Returns: JSON with IoC matches, summary, and metadata Raises: HTTPException: If scan_id is invalid or scan not found
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | The unique scan ID |
Response
{
"scan_id": "string",
"url": "string",
"scan_status": "string",
"submitted_at": "string",
"summary": {
"total_matches": "integer",
"unique_indicators": "integer",
"ip_matches": "integer",
"domain_matches": "integer",
"threat_types": "array",
"has_threats": "boolean"
},
"matches": "array"
}Example
Request
curl "https://scanmalware.com/api/v1/ioc/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://example.com",
"scan_status": "completed",
"submitted_at": "2025-09-19T10:00:00Z",
"summary": {
"total_matches": 2,
"unique_indicators": 2,
"ip_matches": 1,
"domain_matches": 1,
"threat_types": ["phishing", "malware"],
"has_threats": true
},
"matches": [
{
"indicator": "192.168.1.100",
"indicator_type": "ip",
"threat_type": "malware",
"sources": ["abuse.ch", "blocklist.de"],
"context": {
"found_in": "network_request",
"location": "https://example.com/api/track"
}
}
]
}/api/v1/ct/{domain}Certificates for a Domain
Certificates seen in Certificate Transparency logs for a domain, its www host, and its subdomains, newest first (max 100, deduplicated by certificate hash). Useful for subdomain discovery, but it only sees hosts that hold a certificate and is capped at 100 certs — for enumeration use /api/v1/ct/dns/{domain} instead. See the “Finding subdomains” guide at /api-docs#finding-subdomains for how this compares with the other sources.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
domain | string | Required | Domain to look up. Matches the domain, www.<domain>, and *.<domain>. |
Response
{
"domain": "string",
"found": "boolean",
"certificates": [
{
"domain": "string",
"hash": "string",
"timestamp": "integer",
"log": "string",
"ip_addresses": "array"
}
],
"total": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/ct/cloudflare.com"Response
{
"domain": "cloudflare.com",
"found": true,
"certificates": [
{
"domain": "editor-staging.cloudflare.com",
"hash": "b0a3ebeb0561a4cfc0d99ef04e3806fe3e5061f4",
"timestamp": 1787345670369,
"log": "x",
"ip_addresses": ["104.18.27.39", "104.18.26.39"]
}
],
"total": 33
}/api/v1/ct/similar/{domain}Similar Domains
Domains that look similar to the target, discovered from Certificate Transparency data.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
domain | string | Required | The domain to find lookalikes for |
Response
{
"target": "string",
"base_domain": "string",
"similar_domains": "array",
"count": "integer",
"ips_checked": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/ct/similar/paypal.com"Response
{
"target": "paypal.com",
"base_domain": "paypal.com",
"similar_domains": [],
"count": 0,
"ips_checked": 0
}/api/v1/hosts/{domain}Hosts a Domain Touched
Every host seen for a domain, grouped by HOW we learned about it. The default is the two runtime-observed sources plus stream: observed and scripts are hosts the browser really contacted, while stream is a host a third party asked us about that we then confirmed resolves in DNS — existence only, never fetched by us. Ask for sources=observed,scripts to get the contacted-only answer, and opt into the weaker static/referenced sources explicitly. Pass subdomains_only=true for just the subdomains. For a fuller picture of what merely EXISTS, see /api/v1/ct/dns/{domain}, which draws on certificate transparency instead.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
domain | string | Required | Domain to collect hosts for. Scans of the domain and of its subdomains are aggregated. |
sources | string | Optional | Comma-separated. observed = the browser resolved and requested it. scripts = a script the browser actually loaded. declared = named in the page's Content-Security-Policy, i.e. intent and NOT contact. static = called from a URL sink in script source; roughly a third are corroborated by runtime, the rest being conditional or dead code. referenced = appears only in a string literal or comment, a reference rather than an endpoint. stream = a third party queried this host against our API and it resolves in DNS; we have never fetched it, so it evidences existence and nothing else, and hosts under a DNS wildcard are excluded because there existence cannot be confirmed. Default: observed,scripts,stream. |
subdomains_only | boolean | Optional | Return only hosts strictly below the domain. Default false. |
max_scans | integer | Optional | Newest scans of this domain to aggregate over, 1-1000. Default 200. |
limit | integer | Optional | Maximum hosts per source, 1-10000. Default 2000. Check the truncated map. |
Response
{
"domain": "string",
"scans_examined": "integer",
"sources": "object",
"source_meaning": "object",
"truncated": "object",
"hosts": "array",
"host_count": "integer",
"subdomains": "array",
"subdomain_count": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/hosts/cloudflare.com?sources=observed,scripts,declared&subdomains_only=true"Response
{
"domain": "cloudflare.com",
"scans_examined": 200,
"sources": {
"observed": ["aim.cloudflare.com", "api.cloudflare.com"],
"scripts": ["cdnjs.cloudflare.com"],
"declared": ["static.cloudflareinsights.com"]
},
"source_meaning": {
"observed": "browser resolved and requested it",
"scripts": "a script the browser actually loaded",
"declared": "named in the page Content-Security-Policy; intent, not contact"
},
"truncated": {"observed": false, "scripts": false, "declared": false},
"hosts": ["aim.cloudflare.com", "api.cloudflare.com", "cdnjs.cloudflare.com"],
"host_count": 3,
"subdomains": ["aim.cloudflare.com", "api.cloudflare.com", "cdnjs.cloudflare.com"],
"subdomain_count": 3
}/api/v1/ct/dns/{domain}DNS History & Subdomains
DNS observations for a domain and its subdomains, from Certificate Transparency-derived DNS data. Pass include_subdomains=false for the apex only (much faster). ip_addresses covers the apex and www only — each subdomain's own IPs are in its record's ip field. A record's ip is often empty and that is meaningful rather than missing: it means the hostname was published in a certificate but did not resolve when observed, and resolution_error on the same record says why (e.g. nxdomain). dns_records is capped at the 100 most recent observations; subdomains is capped at subdomain_limit (default 2000, max 5000) and subdomains_truncated is true when that cap was reached. This is the primary subdomain-enumeration endpoint. See the “Finding subdomains” guide at /api-docs#finding-subdomains for how this compares with the other sources.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
domain | string | Required | The domain to look up |
include_subdomains | boolean | Optional | Include *.domain records and enumerate distinct subdomains. Default true. Set false for apex-only results, which are considerably faster. |
subdomain_limit | integer | Optional | Maximum distinct subdomains to return, 1-5000. Default 2000. Check subdomains_truncated to see whether the cap was reached. |
Response
{
"domain": "string",
"dns_records": [
{
"domain": "string",
"ip": "array",
"record_type": "string",
"timestamp": "string",
"ttl": "integer",
"root_domain": "string",
"resolution_error": "string|null"
}
],
"ip_addresses": "array",
"total_records": "integer",
"subdomains": "array",
"subdomain_count": "integer",
"subdomains_truncated": "boolean"
}Example
Request
curl "https://scanmalware.com/api/v1/ct/dns/wpsec.com"Response
{
"domain": "wpsec.com",
"dns_records": [
{
"domain": "blog.wpsec.com",
"ip": ["172.66.43.65", "172.66.40.191"],
"record_type": "A",
"timestamp": "2026-08-15T02:01:55",
"ttl": 300,
"root_domain": "wpsec.com"
}
],
"ip_addresses": ["172.66.43.65", "172.66.40.191"],
"total_records": 19,
"subdomains": [
"api-stage.wpsec.com",
"api.wpsec.com",
"blog.wpsec.com",
"mail.wpsec.com"
],
"subdomain_count": 9,
"subdomains_truncated": false
}/api/v1/ct/ip/{ip}Certificates by IP Address
Domains observed resolving to an IP address, with how many DNS records back each. Returns subdomains of a target only when they happen to share that IP; it is better suited to finding unrelated neighbours on shared hosting. See the “Finding subdomains” guide at /api-docs#finding-subdomains for how this compares with the other sources.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
ip | string | Required | The IP address to search |
Response
{
"ip": "string",
"domains": [
{
"domain": "string",
"record_count": "integer"
}
],
"total": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/ct/ip/104.16.132.229"Response
{
"ip": "104.16.132.229",
"domains": [
{
"domain": "virtualhubs.net",
"record_count": 23
}
],
"total": 100
}/api/v1/ct/timeline/{domain}Certificate Timeline
Get certificate issuance timeline for a domain Shows when certificates were issued over time
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
domain | string | Required | Domain name (e.g. example.com), or an IP address. |
days | integer | Optional | Limit timeline to certificates seen in the last N days. Omit to return full history. |
Example
Request
curl "https://scanmalware.com/api/v1/ct/timeline/example.com?days=90"Response
{
"domain": "example.com",
"timeline": [
{
"date": "2025-09-29T00:00:00.000Z",
"certificate_count": 4,
"unique_certificates": 2
},
{
"date": "2025-12-01T00:00:00.000Z",
"certificate_count": 3,
"unique_certificates": 1
}
],
"certificate_changes": [
{
"hash": "5a1b...",
"occurrences": 6,
"first_seen": "2025-09-29T08:14:32.000Z",
"last_seen": "2025-12-15T11:02:08.000Z"
}
],
"total_certificates": 7
}/api/v1/jsfingerprints/search/fuzzy/{fuzzy_hash}Search by Fuzzy Hash (Detailed Results)
Search by SSDEEP fuzzy hash for finding code variants and modified scripts.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
fuzzy_hash | string | Required | SSDEEP fuzzy hash |
limit | integer | Optional | Results per page (1-100, default: 50) |
offset | integer | Optional | Results offset (default: 0) |
Response
{
"results": "array",
"total": "integer",
"search_type": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/search/fuzzy/96:aBcDeFg..."Response
{
"results": [...],
"total": 23,
"search_type": "fuzzy"
}/api/v1/jsfingerprints/search/library/{library}Search by Library Name (Detailed Results)
Search JavaScript by detected library name. Returns all versions and occurrences.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
library | string | Required | Library name (e.g., jquery, react, vue) |
limit | integer | Optional | Results per page (1-100, default: 50) |
offset | integer | Optional | Results offset (default: 0) |
Response
{
"results": "array",
"total": "integer",
"search_type": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/search/library/jquery"Response
{
"results": [...],
"total": 1234,
"search_type": "library"
}/api/v1/jsfingerprints/search/library/{library}/version/{version}Search by Library + Version (Detailed Results)
Find specific library version usage. Essential for tracking vulnerable versions and CVE impact.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
library | string | Required | Library name |
version | string | Required | Library version |
limit | integer | Optional | Results per page (1-100, default: 50) |
offset | integer | Optional | Results offset (default: 0) |
Response
{
"results": "array",
"total": "integer",
"search_type": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/search/library/jquery/version/3.6.0"Response
{
"results": [...],
"total": 567,
"search_type": "library_version"
}/api/v1/jsfingerprint/library-inventoryLibrary Version Inventory
Get comprehensive catalog of all detected JavaScript library versions with usage statistics and prevalence data. Useful for dependency tracking, version auditing, and understanding library adoption across scanned sites.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
library | string | Optional | Filter to specific library (e.g., "jquery", "react") |
min_count | number | Optional | Minimum fingerprint count (default: 10) |
Response
{
"library_filter": "string | null",
"min_count": "number",
"total_library_versions": "number",
"library_versions": "array",
"note": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/library-inventory?library=jquery&min_count=100"Response
{
"library_filter": "jquery",
"min_count": 100,
"total_library_versions": 12,
"library_versions": [
{
"library_name": "jquery",
"version": "3.7.1",
"fingerprint_count": 1200,
"unique_scans": 1191,
"first_seen": "2025-10-11T19:11:50.534385Z",
"last_seen": "2025-11-05T10:28:25.392293Z"
},
{
"library_name": "jquery",
"version": "1.12.0",
"fingerprint_count": 585,
"unique_scans": 584,
"first_seen": "2025-10-09T14:13:17.983428Z",
"last_seen": "2025-11-04T06:23:14.504652Z"
}
],
"note": "This endpoint returns version inventory only. For vulnerability detection, integrate with CVE databases (NVD, Snyk, etc.)."
}/api/v1/jsfingerprint/cdn/{cdn_type}CDN Search
Analyze JavaScript files delivered via specific CDNs. Includes cache status breakdown, top domains, and unpinned script detection.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
cdn_type | string | Required | CDN provider (e.g., 'cloudflare', 'fastly', 'akamai') |
cdn_cache_status | string | Optional | Cache status (HIT, MISS, STALE) |
unpinned_only | boolean | Optional | Only URLs without version pinning |
limit | integer | Optional | Max results |
Response
{
"cdn_type": "string",
"total_scripts": "number",
"unique_scans": "number",
"cache_status_breakdown": "object",
"top_domains": "array",
"unpinned_scripts_count": "number",
"scripts": "array"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/cdn/cloudflare?limit=5"Response
{
"cdn_type": "cloudflare",
"total_scripts": 595,
"unique_scans": 487,
"cache_status_breakdown": {
"HIT": 423,
"MISS": 89,
"DYNAMIC": 83
},
"top_domains": [
{"domain": "cdn.example.com", "count": 142},
{"domain": "static.site.com", "count": 89}
],
"unpinned_scripts_count": 234,
"scripts": [
{
"fingerprint_id": 12350,
"scan_id": "550e8400-e29b-41d4-a716-446655440005",
"script_url": "https://cdnjs.cloudflare.com/ajax/libs/jquery/3.6.0/jquery.min.js",
"cache_status": "HIT",
"created_at": "2025-09-21T10:00:00.000Z"
}
]
}/api/v1/jsfingerprint/server/{server_type}Server Type Search
Find JavaScript files served by specific server types. Includes HTTP header analysis for server fingerprinting.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
server_type | string | Required | Server type (e.g., 'nginx', 'apache', 'cloudflare') |
include_headers | boolean | Optional | Include full HTTP headers |
limit | integer | Optional | Max results |
Response
{
"server_type": "string",
"total_scripts": "number",
"unique_scans": "number",
"scripts": "array"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/server/nginx?limit=5"Response
{
"server_type": "nginx",
"total_scripts": 14804,
"unique_scans": 9872,
"scripts": [
{
"fingerprint_id": 12351,
"scan_id": "550e8400-e29b-41d4-a716-446655440006",
"script_url": "https://nginx-site.com/js/app.js",
"http_headers": {
"server": "nginx/1.21.0",
"content-type": "application/javascript"
},
"created_at": "2025-09-22T11:30:00.000Z"
}
]
}/api/v1/jsfingerprint/obfuscatedObfuscation Search
Hunt for obfuscated JavaScript. Essential for malware detection. Supports score filtering, classification, and library exclusion.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
min_score | number | Optional | Minimum obfuscation score |
max_score | number | Optional | Maximum obfuscation score |
classification | string | Optional | Filter by classification |
exclude_libraries | boolean | Optional | Exclude known libraries |
min_code_length | integer | Optional | Minimum code size |
page | integer | Optional | Page number |
per_page | integer | Optional | Results per page |
Response
{
"obfuscation_filter": {
"min_score": "number",
"max_score": "integer",
"classification": "null"
},
"total_matches": "integer",
"unique_scans": "integer",
"page": "integer",
"per_page": "integer",
"total_pages": "integer",
"scripts": [
{
"fingerprint_id": "integer",
"scan_id": "string",
"script_url": "string",
"obfuscation_score": "integer",
"classification": "string | null",
"confidence": "string | null",
"token_entropy": "number",
"code_length": "integer",
"library_detected": "string | null",
"is_bundled": "boolean | null",
"created_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/obfuscated?min_score=0.7&per_page=5"Response
{
"obfuscation_filter": {
"min_score": 0.7,
"max_score": 1,
"classification": null
},
"total_matches": 10924,
"unique_scans": 6845,
"page": 1,
"per_page": 50,
"total_pages": 219,
"scripts": [
{
"fingerprint_id": 9273307,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://sharp-code-225.cf-7ap0eij2.workers.dev/secureproxy?e=jscdn/getFile",
"obfuscation_score": 1,
"classification": "heavily_obfuscated",
"confidence": "high",
"token_entropy": 10.0278,
"code_length": 4729947,
"library_detected": null,
"is_bundled": null,
"created_at": "2026-09-02T00:50:25.659079Z"
},
{
"fingerprint_id": 1861828,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://marketing-assets.calendly.com/_next/static/chunks/8e7bfb0f8f5b1039.js",
"obfuscation_score": 1,
"classification": "heavily_obfuscated",
"confidence": "high",
"token_entropy": 10.0074,
"code_length": 19432619,
"library_detected": null,
"is_bundled": null,
"created_at": "2025-12-26T00:23:10.307602Z"
}
]
}/api/v1/jsfingerprint/patternsPattern-Based Search
Advanced pattern detection for security research. Finds scripts without library detection, CDN mismatches, and high entropy content.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
has_eval | boolean | Optional | Contains eval() calls |
has_crypto | boolean | Optional | Contains crypto operations |
has_websocket | boolean | Optional | Contains WebSocket usage |
high_entropy | boolean | Optional | High string entropy (suspicious) |
no_library | boolean | Optional | No library detected |
cdn_mismatch | boolean | Optional | CDN URL but no library detected |
limit | integer | Optional | Max results |
Response
{
"total_matches": "number",
"patterns_detected": "object",
"scripts": "array"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/patterns?no_library=true&limit=5"Response
{
"total_matches": 3,
"patterns_detected": {
"no_library": true,
"cdn_mismatch": false,
"high_entropy": false
},
"scripts": [
{
"fingerprint_id": 12353,
"scan_id": "550e8400-e29b-41d4-a716-446655440008",
"script_url": "https://unknown-origin.com/script.js",
"library_detected": null,
"entropy": 7.2,
"obfuscation_score": 0.65,
"created_at": "2025-09-24T15:00:00.000Z"
}
]
}/api/v1/jsfingerprints/search/bundler/{bundler}Search by Bundler Type (Detailed Results)
Search by bundler type (webpack, rollup, vite, parcel). Useful for build tool analysis.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
bundler | string | Required | Bundler type |
limit | integer | Optional | Results per page (1-100, default: 50) |
offset | integer | Optional | Results offset (default: 0) |
Response
{
"results": "array",
"total": "integer",
"search_type": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/search/bundler/webpack"Response
{
"results": [...],
"total": 3456,
"search_type": "bundler"
}/api/v1/jsfingerprint/similar-by-hashML Similarity Search
Find similar scripts by providing content hash (not fingerprint ID). Use Case: Public malware detection without requiring existing fingerprint Performance: 100-500ms (indexed vector search) ML Model: 192-dimensional composite vector (post-strip-ML cut-over) - AST Features (128 dims, weight 5.0x) - Abstract syntax tree analysis - Hand-crafted Features (64 dims, weight 3.0x) - Code complexity metrics
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
content_sha256 | string | Required | SHA-256 hash of target script |
threshold | number | Optional | Similarity threshold 0.0-1.0 (default: 0.8) |
limit | number | Optional | Maximum results (default: 10, max: 100) |
exclude_exact_matches | boolean | Optional | Exclude identical hashes (default: false) |
Response
{
"query_hash": "string",
"query_fingerprint_id": "number",
"threshold": "number",
"results_count": "number",
"similar_fingerprints": "array",
"similarity_interpretation": "object"
}Example
Request
curl -X POST "https://scanmalware.com/api/v1/jsfingerprint/similar-by-hash" \
-H "Content-Type: application/json" \
-d '{
"content_sha256": "817ab96b9d8ea9bfed8fe579563f06c1b3f84acf951b272cc7508e15a3e4cf10",
"threshold": 0.7,
"limit": 5
}'Response
{
"query_hash": "817ab96b9d8ea9bfed8fe579563f06c1b3f84acf951b272cc7508e15a3e4cf10",
"query_fingerprint_id": 12345,
"threshold": 0.7,
"results_count": 5,
"similar_fingerprints": [
{
"fingerprint_id": 12355,
"similarity": 0.94,
"scan_id": "550e8400-e29b-41d4-a716-446655440010",
"script_url": "https://variant.com/modified.js",
"content_sha256": "different_hash",
"library_detected": "custom",
"obfuscation_score": 0.45,
"created_at": "2025-09-26T17:30:00.000Z"
}
],
"similarity_interpretation": {
"0.95-1.0": "Near-identical code",
"0.85-0.95": "Strong similarity",
"0.7-0.85": "Moderate similarity",
"below_0.7": "Low similarity"
}
}/api/v1/scans/{scan_id}/jsfingerprintsList JavaScript Fingerprints for Scan
Get all JavaScript fingerprints for a specific scan with comprehensive analysis data including hashes, metrics, library detection, bundle analysis, obfuscation detection, and more. Returns 91 fields of fingerprinting data across multiple categories.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
include_functions | boolean | Optional | Include full function list (default: false) |
include_http_headers | boolean | Optional | Include HTTP header data (default: true) |
include_vectors_info | boolean | Optional | Include ML vector availability (default: true) |
Response
{
"scan_id": "string",
"total_scripts": "integer",
"fingerprints_count": "integer",
"fingerprints": "array of fingerprint objects with hashes, metrics, ml_vectors, library_detection, copyright, functions, module_info, cdn_info, bundle_analysis, http_headers, obfuscation"
}Example
Request
curl "https://scanmalware.com/api/v1/scans/550e8400-e29b-41d4-a716-446655440000/jsfingerprints"Response
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"total_scripts": 5,
"fingerprints_count": 5,
"fingerprints": [
{
"id": 12345,
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"script_url": "https://example.com/app.js",
"hashes": {
"sha256": "817ab96b9d8ea9bfed8fe579563f06c1b3f84acf951b272cc7508e15a3e4cf10",
"normalized": "bd6ebc7a6b5a920a34ff16367d8dcf2ee0a83e625486f282d4ca76de03275fe7"
},
"metrics": {
"code_length": 45678,
"function_count": 234,
"complexity_score": 156
},
"library_detection": {
"detected": true,
"primary_library": "react",
"version": "18.2.0"
}
}
]
}/api/v1/jsfingerprints/{fingerprint_id}Get Single JavaScript Fingerprint
Retrieve comprehensive analysis of a single JavaScript fingerprint by ID. Returns all 91 fields including 9 hash types, 12 code metrics, ML vector dimensions, library detection, copyright info, function analysis, module detection, CDN fingerprinting, bundle analysis, HTTP headers, and obfuscation metrics.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
fingerprint_id | integer | Required | Fingerprint ID |
include_functions | boolean | Optional | Include full function list (default: false) |
include_http_headers | boolean | Optional | Include HTTP header data (default: true) |
Response
{
"id": "integer",
"scan_id": "string",
"script_url": "string",
"hashes": "object with sha256, normalized, function_composite, fuzzy, string_set, call_graph, import_hash, export_hash, dependency",
"metrics": "object with code_length, function_count, complexity_score, ast metrics",
"ml_vectors": "object with availability flags and dimensions for AST (128), handcrafted (64), composite (192). Legacy semantic-model fields (CodeBERT/GraphCodeBERT, 768d each) appear only on historical fingerprints.",
"library_detection": "object with detected, primary_library, version, confidence",
"copyright": "object with licenses, authors, version_from_header",
"functions": "object with function analysis",
"module_info": "object with module pattern, detected_modules",
"cdn_info": "object with cdn_type, is_cdn, cache data",
"bundle_analysis": "object with is_bundled, bundler_type, bundle_format",
"http_headers": "object with server, content_encoding, cache_control, CDN headers, CORS",
"obfuscation": "object with score, metrics, is_obfuscated, complexity"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/12345"Response
{
"id": 12345,
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"script_url": "https://example.com/app.js",
"hashes": {
"sha256": "817ab96b...",
"normalized": "bd6ebc7a...",
"fuzzy": "96:aBcD..."
},
"ml_vectors": {
"available": true,
"composite_vector_available": true,
"dimensions": {
"ast_features": 128,
"handcrafted": 64,
"composite": 192
}
}
}/api/v1/jsfingerprints/{fingerprint_id}/similarFind Similar JavaScript Using ML
Find JavaScript files structurally similar to the given fingerprint using vector similarity. Uses a 192-dimensional composite vector combining AST features and code complexity metrics. Perfect for malware variant detection and code reuse analysis.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
fingerprint_id | integer | Required | Fingerprint ID |
threshold | number | Optional | Minimum similarity score |
limit | integer | Optional | Maximum results |
offset | integer | Optional | Results offset for pagination |
exclude_same_scan | boolean | Optional | Exclude results from same scan |
Response
{
"query_fingerprint_id": "integer",
"query_script_url": "string",
"threshold": "float",
"results_count": "integer",
"similar_fingerprints": "array of objects with fingerprint_id, script_url, similarity, scan_id, library_detected, code_length, function_count"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/12345/similar?threshold=0.80&limit=20"Response
{
"query_fingerprint_id": 12345,
"threshold": 0.80,
"results_count": 15,
"similar_fingerprints": [
{
"fingerprint_id": 12355,
"similarity": 0.94,
"script_url": "https://variant.com/modified.js",
"scan_id": "550e8400-e29b-41d4-a716-446655440010",
"library_detected": "custom",
"code_length": 45890
}
]
}/api/v1/jsfingerprints/search/sha256/{hash_value}Search by SHA-256 (Detailed Results)
Search JavaScript fingerprints by exact SHA-256 hash. Alternative endpoint to /jsfingerprint/search/sha256 with detailed fingerprint metadata.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_value | string | Required | SHA-256 hash value |
limit | integer | Optional | Results per page (1-100, default: 50) |
offset | integer | Optional | Results offset (default: 0) |
Response
{
"results": "array of objects with scan_id, url, scanned_at, script_url, library_name, library_version, bundler_type, content_sha256",
"total": "integer",
"page": "integer",
"search_type": "string",
"search_value": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/search/sha256/817ab96b9d8ea9bfed8fe579563f06c1b3f84acf951b272cc7508e15a3e4cf10"Response
{
"results": [
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"url": "https://example.com",
"scanned_at": "2025-11-23T10:30:00.000Z",
"script_url": "https://example.com/app.js",
"library_name": "react",
"library_version": "18.2.0"
}
],
"total": 42,
"search_type": "sha256"
}/api/v1/jsfingerprints/search/normalized/{hash_value}Search by Normalized Hash (Detailed Results)
Search by normalized SHA-256 hash (whitespace-independent). Finds functionally identical code with different formatting.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_value | string | Required | Normalized SHA-256 hash value |
limit | integer | Optional | Results per page (1-100, default: 50) |
offset | integer | Optional | Results offset (default: 0) |
Response
{
"results": "array",
"total": "integer",
"search_type": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/search/normalized/bd6ebc7a6b5a920a34ff16367d8dcf2ee0a83e625486f282d4ca76de03275fe7"Response
{
"results": [...],
"total": 87,
"search_type": "normalized"
}/api/v1/jsfingerprints/statistics/bundlesGet Bundle Statistics
Get comprehensive statistics about bundled JavaScript usage including bundling rate, bundler type breakdown (webpack, rollup, etc.), bundle format distribution, and average sizes.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
from_date | string | Optional | Start date (ISO 8601) |
to_date | string | Optional | End date (ISO 8601) |
Response
{
"time_range": {
"from": "null",
"to": "null"
},
"total_fingerprints": "integer",
"bundled_count": "integer",
"bundled_percentage": "number",
"unbundled_count": "integer",
"bundler_breakdown": {
"unknown": {
"count": "integer",
"percentage": "number",
"average_size": "integer",
"average_functions": "integer"
},
"requirejs": {
"count": "integer",
"percentage": "number",
"average_size": "integer",
"average_functions": "integer"
},
"webpack": {
"count": "integer",
"percentage": "number",
"average_size": "integer",
"average_functions": "integer"
},
"browserify": {
"count": "integer",
"percentage": "number",
"average_size": "integer",
"average_functions": "integer"
},
"vite": {
"count": "integer",
"percentage": "number",
"average_size": "integer",
"average_functions": "integer"
},
"parcel": {
"count": "integer",
"percentage": "number",
"average_size": "integer",
"average_functions": "integer"
},
"rollup": {
"count": "integer",
"percentage": "number",
"average_size": "integer",
"average_functions": "integer"
},
"systemjs": {
"count": "integer",
"percentage": "number",
"average_size": "integer",
"average_functions": "integer"
},
"esbuild": {
"count": "integer",
"percentage": "integer",
"average_size": "integer",
"average_functions": "integer"
}
},
"format_breakdown": {
"unknown": {
"count": "integer",
"percentage": "number"
},
"amd": {
"count": "integer",
"percentage": "number"
},
"cjs": {
"count": "integer",
"percentage": "number"
},
"iife": {
"count": "integer",
"percentage": "integer"
},
"umd": {
"count": "integer",
"percentage": "number"
},
"esm": {
"count": "integer",
"percentage": "number"
}
}
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/statistics/bundles"Response
{
"time_range": {
"from": null,
"to": null
},
"total_fingerprints": 8716116,
"bundled_count": 227330,
"bundled_percentage": 2.6,
"unbundled_count": 8488786,
"bundler_breakdown": {
"unknown": {
"count": 50844,
"percentage": 22.4,
"average_size": 72312,
"average_functions": 448
},
"requirejs": {
"count": 34690,
"percentage": 15.3,
"average_size": 78365,
"average_functions": 298
},
"webpack": {
"count": 19684,
"percentage": 8.7,
"average_size": 211767,
"average_functions": 972
},
"browserify": {
"count": 4147,
"percentage": 1.8,
"average_size": 117163,
"average_functions": 499
},
"vite": {
"count": 4061,
"percentage": 1.8,
"average_size": 278981,
"average_functions": 1069
},
"parcel": {
"count": 1576,
"percentage": 0.7,
"average_size": 150297,
"average_functions": 770
},
"rollup": {
"count": 618,
"percentage": 0.3,
"average_size": 466714,
"average_functions": 1652
},
"systemjs": {
"count": 254,
"percentage": 0.1,
"average_size": 39295,
"average_functions": 135
},
"esbuild": {
"count": 27,
"percentage": 0,
"average_size": 825555,
"average_functions": 1547
}
},
"format_breakdown": {
"unknown": {
"count": 149186,
"percentage": 65.6
},
"amd": {
"count": 37195,
"percentage": 16.4
},
"cjs": {
"count": 24214,
"percentage": 10.7
},
"iife": {
"count": 16001,
"percentage": 7
},
"umd": {
"count": 405,
"percentage": 0.2
},
"esm": {
"count": 329,
"percentage": 0.1
}
}
}/api/v1/jsfingerprints/statistics/librariesGet Library Statistics
Get comprehensive statistics about JavaScript library usage including detection rates, top libraries with version breakdowns, license information, and copyright statistics.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
from_date | string | Optional | Start date (ISO 8601) |
to_date | string | Optional | End date (ISO 8601) |
min_count | integer | Optional | Minimum occurrences to include (default: 5) |
Response
{
"time_range": {
"from": "null",
"to": "null"
},
"total_fingerprints": "integer",
"with_library_detection": "integer",
"detection_rate": "number",
"top_libraries": [
{
"name": "string",
"count": "integer",
"percentage": "integer",
"versions": "string",
"average_size": "integer"
}
],
"copyright_statistics": {
"with_copyright": "integer",
"without_copyright": "integer",
"copyright_percentage": "integer"
},
"license_breakdown": {
"MIT": "integer",
"Apache-2.0": "integer",
"BSD-3-Clause": "integer",
"GPL-2.0": "integer",
"BSD": "integer",
"ISC": "integer",
"GPL": "integer",
"GPL-3.0": "integer",
"WTFPL": "integer",
"Unlicense": "integer",
"Apache": "integer",
"BSD-2-Clause": "integer"
}
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/statistics/libraries?min_count=10"Response
{
"time_range": {
"from": null,
"to": null
},
"total_fingerprints": 8716116,
"with_library_detection": 1529742,
"detection_rate": 17.6,
"top_libraries": [
{
"name": "angular",
"count": 122435,
"percentage": 8,
"versions": "{ \"unknown\" : 2, \"unknown\" : 2, \"unknown\" : 1, \"unknown\" : 1, \"2.0\" : 1, \"unknown\" : 1, \"unknown\" : 1, \"unknown\" : 1, \"unknown\" : 1, \"unknown\" : 1, \"unknown\"...",
"average_size": 444214
},
{
"name": "react",
"count": 48106,
"percentage": 3.1,
"versions": "{ \"unknown\" : 2, \"1.0.0\" : 1, \"unknown\" : 1, \"16.13.1\" : 1, \"unknown\" : 2, \"unknown\" : 1, \"unknown\" : 1, \"unknown\" : 1, \"1.2.18\" : 1, \"unknown\" : 1, \"unknown...",
"average_size": 440885
}
],
"copyright_statistics": {
"with_copyright": 3141514,
"without_copyright": 5574602,
"copyright_percentage": 36
},
"license_breakdown": {
"MIT": 312998,
"Apache-2.0": 312822,
"BSD-3-Clause": 13729,
"GPL-2.0": 7482,
"BSD": 5711,
"ISC": 4592,
"GPL": 4539,
"GPL-3.0": 3029,
"WTFPL": 2809,
"Unlicense": 559,
"Apache": 422,
"BSD-2-Clause": 96
}
}/api/v1/jsfingerprints/hash-prevalence/{scan_id}Get Hash Prevalence for Scan
Get prevalence counts for all script hashes in a scan. Shows how many other scans contain matching content (exact SHA-256), normalized hash, and fuzzy hash availability. Helps identify commonly used libraries vs unique scripts.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan ID |
Response
{
"scan_id": "string",
"fingerprint_count": "integer",
"prevalence": [
{
"fingerprint_id": "integer",
"script_url": "string",
"prevalence": {
"exact_matches": "integer",
"normalized_matches": "integer",
"has_fuzzy_hash": "boolean",
"interpretation": "string"
}
}
],
"note": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/hash-prevalence/550e8400-e29b-41d4-a716-446655440000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"fingerprint_count": 82,
"prevalence": [
{
"fingerprint_id": 9309578,
"script_url": "https://repliers.com/wp-includes/js/jquery/jquery.min.js?ver=3.7.1",
"prevalence": {
"exact_matches": 26745,
"normalized_matches": 25669,
"has_fuzzy_hash": true,
"interpretation": "widespread"
}
},
{
"fingerprint_id": 9309579,
"script_url": "https://repliers.com/wp-includes/js/jquery/jquery-migrate.min.js?ver=3.4.1",
"prevalence": {
"exact_matches": 24176,
"normalized_matches": 23326,
"has_fuzzy_hash": true,
"interpretation": "widespread"
}
}
],
"note": "Counts show number of OTHER scans (excluding this one) with matching hashes"
}/api/v1/jsfingerprints/{fingerprint_id}/similarity-countsGet ML Similarity Counts by Algorithm
Get count of similar scripts for EACH ML algorithm separately. Returns similarity counts for: - CodeBERT (768-dim semantic code embedding) - GraphCodeBERT (768-dim graph-based embedding) - AST Features (128-dim structural metrics) - Handcrafted Features (64-dim complexity metrics) - Composite Vector (192-dim weighted combination of AST + handcrafted) Uses cosine similarity (1 - distance) where 1.0 = identical, 0.0 = opposite. **Performance Note**: Uses LIMIT-based counting for efficiency. Counts are capped at max_count. If count equals max_count, actual count may be higher (indicated by 'capped' flag). Composite vector search is optimized via HNSW index.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
fingerprint_id | integer | Required | Fingerprint ID |
threshold | number | Optional | Minimum similarity score |
max_count | integer | Optional | Max count to return (for performance) |
Response
{
"fingerprint_id": "integer",
"threshold": "float",
"similarity_counts": "object with counts for semantic_a, semantic_b, ast_features, handcrafted_features, composite"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/12345/similarity-counts?threshold=0.85"Response
{
"fingerprint_id": 12345,
"threshold": 0.85,
"similarity_counts": {
"ast_features": {"count": 45, "dimension": 128},
"handcrafted_features": {"count": 38, "dimension": 64},
"composite": {"count": 12, "dimension": 192}
}
}/api/v1/js-fingerprinter2/search/similar/{scan_id}Search Similar Behavioral Fingerprints
Find scans with similar behavioral fingerprints using weighted component comparison. Enables malware variant detection, code reuse identification, and obfuscated code matching using Call Pattern (35%), Characteristics (25%), Signature (15%), API Sequence (15%), Timing (5%), and Sequence Graph (5%).
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan ID to find similar fingerprints |
min_similarity | float | Optional | Minimum similarity threshold (0.0-1.0, default: 0.90) |
limit | integer | Optional | Maximum number of results (1-500, default: 50) |
include_self | boolean | Optional | Include the query scan in results (default: false) |
Response
{
"query_scan_id": "string",
"query_fingerprint": {
"timing": {
"enabled": "boolean",
"stdDev": "integer",
"pattern": "string",
"intervals": [
"integer"
],
"avgInterval": "integer",
"maxInterval": "integer",
"minInterval": "integer",
"commonIntervals": [
"object"
]
},
"enabled": "boolean",
"apiUsage": {
"undefined": "integer",
"fetch": "integer",
"WebSocket": "integer",
"sendBeacon": "integer",
"setTimeout": "integer",
"setInterval": "integer",
"XMLHttpRequest.open": "integer",
"Worker": "integer"
},
"signature": "string",
"timingHash": "string | null",
"callPattern": [
"integer"
],
"sequenceHash": "string | null",
"compositeHash": "string",
"sequenceGraph": {
"enabled": "boolean",
"edges": "integer",
"nodes": "integer",
"cycles": [
"object"
],
"topPaths": [
"object"
],
"topSequences": [
"object"
]
},
"behaviorVector": [
"integer"
],
"apiSequenceHash": "string | null",
"characteristics": {
"evalCalls": "integer",
"totalSamples": "integer",
"totalFunctions": "integer",
"apiCallsTracked": "integer",
"domManipulation": "integer",
"functionConstructorCalls": "integer"
},
"stableSignature": "string",
"behaviorVectorHex": "string",
"stableSignatureHash": "string"
},
"threshold": "number",
"matches_found": "integer",
"matches": [
{
"scan_id": "string",
"target_url": "string",
"overall_risk": "string",
"similarity": "integer",
"is_match": "boolean",
"breakdown": {
"callPatternMatch": "number",
"signatureMatch": "integer",
"characteristicsMatch": "integer",
"apiSequenceMatch": "integer",
"timingMatch": "integer",
"sequenceMatch": "integer"
},
"created_at": "string"
}
],
"execution_time_ms": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/similar/550e8400-e29b-41d4-a716-446655440000?min_similarity=0.95&limit=20"Response
{
"query_scan_id": "123e4567-e89b-12d3-a456-426614174000",
"query_fingerprint": {
"timing": {
"enabled": false
},
"enabled": true,
"apiUsage": {},
"signature": "simple",
"timingHash": null,
"callPattern": [
100,
57
],
"sequenceHash": null,
"compositeHash": "4690ef9a4f9a0d82b7564bc0a81a8087f71e0a5e0e94cee7180bca96f7335d72",
"sequenceGraph": {
"enabled": false
},
"behaviorVector": [
0,
0
],
"apiSequenceHash": null,
"characteristics": {
"evalCalls": 0,
"totalSamples": 11504,
"totalFunctions": 44,
"apiCallsTracked": 0,
"domManipulation": 0,
"functionConstructorCalls": 0
},
"stableSignature": "ev:none|fc:none|st:none|si:none|ft:none|dw:none|dm:none|E:n|F:n|D:n|W:n|cx:small|vol:none|tp:none|ts:none|ps:gradual|pd:deep|pw:tapered|sq:none|sl:n|tt:none",
"behaviorVectorHex": "00000000000000000055000000ff914a24242424242424400000000000000000",
"stableSignatureHash": "d11b5e2104f362f3b3ec5dea82a52b911e54c2ef63467b360c924acb9519229e"
},
"threshold": 0.9,
"matches_found": 50,
"matches": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"target_url": "https://fgh.ctgerizim.com.br/cgi_bin/?error=login_required&error_description=AADSTS50058%3a+A+silent+sign-in+request+was+sent+but+no+user+is+signed+in.+The+c...",
"overall_risk": "low",
"similarity": 0.9993480528511822,
"is_match": true,
"breakdown": {
"callPatternMatch": 0.9999999999999999,
"signatureMatch": 1,
"characteristicsMatch": 0.9973922114047288,
"apiSequenceMatch": 1,
"timingMatch": 1,
"sequenceMatch": 1
},
"created_at": "2026-08-27T09:55:05.243269+00:00"
},
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"target_url": "https://wbts-prd01-0102.fmapp.cloud/auth/realms/FuturMaster/protocol/openid-connect/auth?client_id=webapp-client&redirect_uri=https%3A%2F%2Fwbts-prd01-0102.f...",
"overall_risk": "low",
"similarity": 0.998913421418637,
"is_match": true,
"breakdown": {
"callPatternMatch": 0.9999999999999999,
"signatureMatch": 1,
"characteristicsMatch": 0.995653685674548,
"apiSequenceMatch": 1,
"timingMatch": 1,
"sequenceMatch": 1
},
"created_at": "2026-08-24T10:27:13.151909+00:00"
}
],
"execution_time_ms": 13529
}/api/v1/js-fingerprinter2/search/composite-hash/{composite_hash}Search by Composite Hash
Find all scans with exact composite hash match. The composite hash is a SHA-256 hash of all behavioral data. Use for finding exact behavioral matches (same code, possibly obfuscated).
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
composite_hash | string | Required | SHA-256 composite hash from behavioral fingerprint |
limit | integer | Optional | Maximum number of results (1-1000, default: 100) |
Response
{
"composite_hash": "string",
"matches_found": "integer",
"matches": "array of objects with scan_id, target_url, overall_risk, created_at"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/composite-hash/abc123def456..."Response
{
"composite_hash": "abc123def456...",
"matches_found": 3,
"matches": [...]
}/api/v1/js-fingerprinter2/search/stable-signature/{signature_hash}Search by Stable Behavioral Signature
Find all scans with matching stable behavioral signature. Stable signatures bucket API usage into categories (none/low/medium/high/very_high) and complexity into tiers, producing deterministic signatures that cluster similar behavior. Unlike composite hash (exact match), this groups scans with similar behavioral patterns even when exact call counts differ.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
signature_hash | string | Required | SHA-256 hash of the stable behavioral signature string |
limit | integer | Optional | Maximum number of results (1-1000, default: 100) |
Response
{
"stable_signature_hash": "string",
"stable_signature": "string (e.g. eval:yes|func_ctor:no|setTimeout:very_high|...)",
"matches_found": "integer",
"matches": "array of objects with scan_id, target_url, overall_risk, stable_signature, created_at"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/stable-signature/94be021cf5bf..."Response
{
"stable_signature_hash": "94be021cf5bf...",
"stable_signature": "eval:no|func_ctor:no|setTimeout:none|setInterval:none|fetch:none|dom:no|docwrite:no|complexity:small|timing:none",
"matches_found": 13,
"matches": [...]
}/api/v1/js-fingerprinter2/search/behavior-vector/similar/{scan_id}Search by Behavior Vector Similarity
Find scans with similar behavior vectors using L1 (Manhattan) distance. The 32-byte behavior vector encodes API usage intensity, code complexity, risk flags, call patterns, timing, and sequence topology. Returns scans ranked by continuous similarity score (0-1), enabling nearest-neighbor behavioral search even when stable signatures differ.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | UUID of the scan to find similar scans for |
min_similarity | float | Optional | Minimum similarity threshold 0-1 (default: 0.7) |
limit | integer | Optional | Maximum number of results (1-200, default: 50) |
Response
{
"scan_id": "string",
"target_vector": "string (64-char hex)",
"min_similarity": "float",
"matches_found": "integer",
"matches": "array of objects with scan_id, target_url, overall_risk, stable_signature, similarity, created_at"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/behavior-vector/similar/4ddc4235-ef75-4f43-b97f-7ce96804270b?min_similarity=0.8&limit=10"Response
{
"scan_id": "4ddc4235-ef75-4f43-b97f-7ce96804270b",
"target_vector": "3a00ff7900005e00...",
"min_similarity": 0.8,
"matches_found": 5,
"matches": [
{"scan_id": "...", "similarity": 0.92, ...}
]
}/api/v1/js-fingerprinter2/search/code-hash/{code_hash}Search by Code Hash
Find all scans containing scripts with exact code hash match. Allows finding identical scripts across different scans, even if served from different URLs. Useful for tracking script prevalence and identifying reused malicious code.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
code_hash | string | Required | SHA-256 hash of individual script code |
limit | integer | Optional | Maximum number of results (1-1000, default: 100) |
Response
{
"code_hash": "string",
"matches_found": "integer",
"matches": "array of objects with scan_id, target_url, script_url, overall_risk, risk_score, created_at"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/code-hash/def456ghi789..."Response
{
"code_hash": "def456ghi789...",
"matches_found": 15,
"matches": [...]
}/api/v1/js-fingerprinter2/search/signature/{signature}Search by Behavior Signature
Find scans with matching behavior signature. Signature format: eval:X|Function:Y|api:count|complexity. Example: eval:15|Function:3|setTimeout:45|medium. Use for quick search of scans with similar API usage patterns.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
signature | string | Required | Human-readable behavior signature |
limit | integer | Optional | Maximum number of results (1-1000, default: 100) |
Response
{
"signature": "string",
"matches_found": "integer",
"matches": "array of objects with scan_id, target_url, overall_risk, signature, characteristics, created_at"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/signature/eval:10|Function:2|medium"Response
{
"signature": "eval:10|Function:2|medium",
"matches_found": 7,
"matches": [...]
}/api/v1/js-fingerprinter2/search/malware-familiesDetect Malware Families
Detect malware families by clustering scans with similar behavioral fingerprints. Uses composite hash + signature matching to group related scans. Use cases: malware family detection, campaign tracking, threat actor attribution, supply chain compromise detection.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
min_cluster_size | integer | Optional | Minimum scans per family (2-100, default: 2) |
similarity_threshold | float | Optional | Similarity threshold for clustering (0.0-1.0, default: 0.95) |
limit | integer | Optional | Maximum number of families to return (1-500, default: 50) |
Response
{
"families_found": "integer",
"total_scans_clustered": "integer",
"families": "array of objects with cluster_id, representative_scan_id, member_count, avg_similarity, composite_hash, signature, members array"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/malware-families?min_cluster_size=3"Response
{
"families_found": 12,
"total_scans_clustered": 456,
"families": [...]
}/api/v1/js-fingerprinter2/search/fingerprint-coverageGet Fingerprint Coverage Statistics
Get statistics on behavioral fingerprint coverage. Shows how many scans have fingerprints enabled vs disabled, unique composite hashes, and unique signatures over the past 30 days.
Response
{
"total_scans": "integer",
"with_fingerprints": "integer",
"without_fingerprints": "integer",
"coverage_percentage": "number",
"unique_composite_hashes": "integer",
"unique_signatures": "integer",
"time_range": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/fingerprint-coverage"Response
{
"total_scans": 52063,
"with_fingerprints": 48630,
"without_fingerprints": 3400,
"coverage_percentage": 93.41,
"unique_composite_hashes": 35535,
"unique_signatures": 14691,
"time_range": "30 days"
}/api/v1/js-fingerprinter2/search/healthJS-Fingerprinter2 Health Check
Health check for JS-Fingerprinter2 search API
Response
{
"status": "string",
"service": "string",
"version": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/health"Response
{
"status": "healthy",
"service": "js-fingerprinter2-search-api",
"version": "1.0.0"
}/api/v1/js-segments/scan/{scan_id}Get Code Segments by Scan ID
Get all code segments for a scan. Returns detailed information about all extracted functions, classes, and code blocks including segment type, function name, location, code snippet, hashes, risk score, library matches, and suspicious flags. Pass script_url to narrow to ONE script; without it the response covers every script in the scan and `scope` reads "scan" rather than "script". Check `scope` before comparing total_count against a single script. Inline scripts (script_url starting `inline://`) are resolved by matching each segment's stored byte range against the script's own content, so `inline_attribution` says whether that check could run: "exact" means an empty result is a real answer about that script, while "unavailable_source_not_stored" or "unavailable_no_content_hash" mean the question could not be answered.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
script_url | string | Optional | Filter by specific script URL |
limit | integer | Optional | Maximum segments to return |
offset | integer | Optional | Pagination offset |
Response
{
"total_count": "integer",
"segments": "array of segment objects with type, function_name, location, code, hashes, risk_score, is_known_library, is_internal_code",
"query_params": "object",
"scope": "string - what total_count counts: 'script' (one script), 'scan' (all scripts in the scan), 'corpus'",
"inline_attribution": "string or null - inline scripts only: 'exact', 'unavailable_source_not_stored', 'unavailable_no_content_hash'"
}Example
Request
curl "https://scanmalware.com/api/v1/js-segments/scan/550e8400-e29b-41d4-a716-446655440000?limit=50"Response
{
"total_count": 234,
"segments": [...],
"query_params": {"scan_id": "...", "limit": 50},
"scope": "scan",
"inline_attribution": null
}/api/v1/js-segments/search/hash/{code_hash}Search Segments by Code Hash
Find all segments with matching exact code hash (SHA-256). Useful for finding identical code segments across different scans.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
code_hash | string | Required | SHA-256 code hash |
limit | integer | Optional | Maximum segments (1-1000, default: 100) |
offset | integer | Optional | Pagination offset (default: 0) |
Response
{
"total_count": "integer",
"segments": "array of segment objects ordered by created_at DESC"
}Example
Request
curl "https://scanmalware.com/api/v1/js-segments/search/hash/abc123..."Response
{
"total_count": 15,
"segments": [...]
}/api/v1/js-segments/search/normalized/{normalized_hash}Search Segments by Normalized Hash
Find all segments with matching normalized code hash. Normalized hashes remove whitespace and comments, enabling fuzzy matching of functionally identical code with different formatting.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
normalized_hash | string | Required | Normalized code hash (whitespace removed) |
limit | integer | Optional | Maximum segments (1-1000, default: 100) |
offset | integer | Optional | Pagination offset (default: 0) |
Response
{
"total_count": "integer",
"segments": "array of segment objects ordered by created_at DESC"
}Example
Request
curl "https://scanmalware.com/api/v1/js-segments/search/normalized/def456..."Response
{
"total_count": 8,
"segments": [...]
}/api/v1/js-segments/search/tlsh/{tlsh_hash}Search Segments by TLSH Similarity
Find code segments similar to a given TLSH hash using fuzzy matching. TLSH (Trend Micro Locality Sensitive Hash) enables finding code variants even when minified, variable-renamed, or slightly modified. Useful for detecting malware variants and code reuse across different sites.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
tlsh_hash | string | Required | TLSH hash to search (must start with "T1", min 70 chars) |
max_distance | integer | Optional | Maximum TLSH distance (0=identical, <50=similar, <100=related, default: 50) |
limit | integer | Optional | Maximum results (1-500, default: 100) |
include_known_libraries | boolean | Optional | Include segments from known libraries (default: false) |
Response
{
"query_hash": "string - The TLSH hash that was searched",
"max_distance": "integer - The distance threshold used",
"total_candidates_scanned": "integer - Number of segments with TLSH hashes checked",
"matches_found": "integer - Number of similar segments found",
"matches": "array of similar segment objects with tlsh_distance and similarity_score",
"tlsh_available": "boolean - Whether TLSH library is available"
}Example
Request
curl "https://scanmalware.com/api/v1/js-segments/search/tlsh/T100D0A7CD7C917404351732BEC06B002B726A0F87144F0420E16804543E75638E727808?max_distance=50&limit=10"Response
{
"query_hash": "T100D0A7CD7C917404351732BEC06B002B726A0F87144F0420E16804543E75638E727808",
"max_distance": 50,
"total_candidates_scanned": 1161,
"matches_found": 1,
"matches": [
{
"segment_id": 312116,
"scan_id": "8105704a-ad40-4ee2-a466-8d9d4ebccd38",
"script_url": "https://ajax.googleapis.com/ajax/libs/jquery/3.6.3/jquery.min.js",
"function_name": "j",
"code_length": 215,
"code_snippet": "function j(e,n,r){return m(n)?E.grep(e,function...",
"tlsh_hash": "T100D0A7CD7C917404351732BEC06B002B726A0F87144F0420E16804543E75638E727808",
"tlsh_distance": 0,
"similarity_score": 1.0,
"risk_score": 25,
"is_known_library": false
}
],
"tlsh_available": true
}/api/v1/js-segments/{scan_id}/unknownGet Unknown Code Segments
Identify segments not matching known libraries. Returns code segments that are not recognized as part of known JavaScript libraries. These are candidates for further malware analysis. Results ordered by risk score and code length.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
min_code_length | integer | Optional | Minimum code length to include (default: 50) |
limit | integer | Optional | Maximum segments (1-1000, default: 100) |
offset | integer | Optional | Pagination offset (default: 0) |
Response
{
"total_count": "integer",
"segments": "array of unknown segment objects ordered by risk_score DESC, code_length DESC"
}Example
Request
curl "https://scanmalware.com/api/v1/js-segments/550e8400-e29b-41d4-a716-446655440000/unknown?min_code_length=100"Response
{
"total_count": 42,
"segments": [...]
}/api/v1/js-segments/{scan_id}/suspiciousGet Suspicious Code Segments
Get high-risk segments that are not known libraries. Returns segments with elevated risk scores (indicating potential malicious code like eval usage, base64 encoding, high entropy, etc.). Results ordered by risk score.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
min_risk_score | integer | Optional | Minimum risk score (0-100, default: 60) |
limit | integer | Optional | Maximum segments (1-1000, default: 100) |
offset | integer | Optional | Pagination offset (default: 0) |
Response
{
"total_count": "integer",
"segments": "array of suspicious segment objects ordered by risk_score DESC"
}Example
Request
curl "https://scanmalware.com/api/v1/js-segments/550e8400-e29b-41d4-a716-446655440000/suspicious?min_risk_score=70"Response
{
"total_count": 5,
"segments": [...]
}/api/v1/js-segments/differentialPerform Differential Analysis
Compare bundle segments against known library database. Analyzes all segments in a scan and identifies: 1) Which segments match known libraries (jQuery, React, etc.), 2) Which segments are unknown (potential malware), 3) Which unknown segments have high risk scores (suspicious). Returns a breakdown of library composition and unknown code.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID (in request body) |
min_confidence | float | Optional | Minimum library match confidence (0.0-1.0, default: 0.8, in request body) |
include_known_libraries | boolean | Optional | Include known libraries in analysis (default: false, in request body) |
Response
{
"scan_id": "string",
"total_segments": "integer",
"matched_segments": "integer",
"unknown_segments": "integer",
"suspicious_segments": "integer",
"library_breakdown": "object mapping library name to segment count",
"unknown_segment_details": "array of unknown segments (max 50)",
"suspicious_segment_details": "array of suspicious segments (max 50)"
}Example
Request
curl -X POST "https://scanmalware.com/api/v1/js-segments/differential" \
-H "Content-Type: application/json" \
-d '{"scan_id": "550e8400-e29b-41d4-a716-446655440000", "min_confidence": 0.85}'Response
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"total_segments": 234,
"matched_segments": 180,
"unknown_segments": 54,
"suspicious_segments": 8,
"library_breakdown": {
"jquery": 45,
"react": 89
},
"unknown_segment_details": [...],
"suspicious_segment_details": [...]
}/api/v1/pcap/{scan_id}Download Packet Capture
Download the decrypted packet capture file for a scan. Returns a gzip-compressed PCAP file containing all HTTP/HTTPS traffic captured during the scan with TLS decrypted.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
Response
{
"content": "Binary gzip-compressed PCAP file",
"headers": "Content-Disposition with filename, X-Scan-Id, X-PCAP-Type"
}Example
Request
curl "https://scanmalware.com/api/v1/pcap/550e8400-e29b-41d4-a716-446655440000" -o scan.pcap.gzResponse
# Binary PCAP file downloaded
# Decompress with: gunzip scan.pcap.gz
# Analyze with: tcpdump -r scan.pcap or wireshark scan.pcap/api/v1/pcap/{scan_id}/metadataGet Packet Capture Metadata
Get metadata about a packet capture file without downloading it. Useful for checking availability and file size before downloading.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
Response
{
"scan_id": "string",
"url": "string",
"status": "string",
"storage_path": "string",
"file_size_bytes": "integer",
"compressed": "boolean",
"content_type": "string",
"created_at": "string",
"scan_created_at": "string",
"available": "boolean"
}Example
Request
curl "https://scanmalware.com/api/v1/pcap/550e8400-e29b-41d4-a716-446655440000/metadata"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://pointdesuture-lesite-com.pages.dev/css/lib/fonts/slick.html",
"status": "completed",
"storage_path": "66/8d/123e4567-e89b-12d3-a456-426614174000.pcap.gz",
"file_size_bytes": 30686,
"compressed": true,
"content_type": "application/gzip",
"created_at": "2026-09-02T18:18:01+00:00",
"scan_created_at": "2026-09-02T18:17:18.939050",
"available": true
}/api/v1/ids/alerts/{scan_id}Get IDS Alerts
Get network intrusion detection alerts for a scan. Returns Suricata IDS alerts triggered during the scan, including signature matches, severity levels, and network flow information.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
Response
{
"scan_id": "string",
"alerts": [
{
"severity": "integer",
"signature_name": "string",
"category": "string",
"protocol": "string",
"src_ip": "string | null",
"src_port": "integer",
"dest_ip": "string | null",
"dest_port": "integer",
"timestamp": "string"
}
],
"total_count": "integer",
"severity_breakdown": {
"1": "integer",
"3": "integer"
}
}Example
Request
curl "https://scanmalware.com/api/v1/ids/alerts/550e8400-e29b-41d4-a716-446655440000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"alerts": [
{
"severity": 3,
"signature_name": "SURICATA HTTP unable to match response to request",
"category": "Generic Protocol Command Decode",
"protocol": "TCP",
"src_ip": "69.163.176.201/32",
"src_port": 443,
"dest_ip": null,
"dest_port": 55861,
"timestamp": "2026-09-02T17:45:14.437003Z"
},
{
"severity": 3,
"signature_name": "SURICATA HTTP invalid response field folding",
"category": "Generic Protocol Command Decode",
"protocol": "TCP",
"src_ip": "69.163.176.201/32",
"src_port": 443,
"dest_ip": null,
"dest_port": 55861,
"timestamp": "2026-09-02T17:45:14.437003Z"
}
],
"total_count": 4,
"severity_breakdown": {
"1": 1,
"3": 3
}
}/api/v1/yara/statsYARA Malware Detection Statistics
Get overall YARA malware detection statistics including total detections, severity distribution, top threats, and detection trends. YARA scanner uses 3633 community rules from 15 repositories.
Response
{
"overall": {
"total_matches": "integer",
"scans_with_matches": "integer",
"unique_patterns": "integer",
"unique_threats": "integer",
"avg_confidence": "number"
},
"recent_24h": {
"matches_24h": "integer",
"scans_24h": "integer",
"patterns_24h": "integer"
},
"severity_distribution": "array",
"category_distribution": "array",
"top_threats": "array",
"timestamp": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/yara/stats"Response
{
"overall": {
"total_matches": 1543,
"scans_with_matches": 892,
"unique_patterns": 287,
"unique_threats": 145,
"avg_confidence": 0.87
},
"recent_24h": {
"matches_24h": 45,
"scans_24h": 28,
"patterns_24h": 12
},
"severity_distribution": [
{"severity": "critical", "count": 156},
{"severity": "high", "count": 432},
{"severity": "medium", "count": 687},
{"severity": "low", "count": 268}
],
"category_distribution": [
{"pattern_category": "cryptominer", "count": 234, "scan_count": 156},
{"pattern_category": "webskimmer", "count": 198, "scan_count": 132}
],
"top_threats": [
{
"pattern_name": "CoinHive Miner",
"severity": "high",
"category": "cryptominer",
"detection_count": 89,
"scan_count": 67,
"last_detected": "2025-01-07T14:23:00Z"
}
],
"timestamp": "2025-01-07T15:30:00.000Z"
}/api/v1/yara/threats/recentRecent YARA Threat Detections
Get recently detected YARA threats across all scans, sorted by detection time. Useful for real-time threat monitoring and security intelligence.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hours | integer | Optional | Hours to look back (1-168, default: 24) |
limit | integer | Optional | Maximum results (1-1000, default: 100) |
Response
{
"threats": "array of threat objects",
"count": "integer",
"hours": "integer",
"timestamp": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/yara/threats/recent?hours=48&limit=50"Response
{
"threats": [
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"url": "https://example.com",
"rule_name": "webskimmer_magecart",
"pattern_name": "Magecart Payment Skimmer",
"category": "webskimmer",
"severity": "critical",
"threat_names": ["Magecart", "FormGrabber"],
"confidence": 0.95,
"detected_at": "2025-01-07T14:23:00Z"
}
],
"count": 23,
"hours": 48,
"timestamp": "2025-01-07T15:30:00.000Z"
}/api/v1/yara/scan/{scan_id}YARA Matches for Scan
Get all YARA malware pattern matches for a specific scan. Returns matched rules with severity, threat names, CVE IDs, MITRE techniques, and matched strings.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
Response
{
"scan_id": "string",
"matches": "array of match objects",
"summary": {
"total_matches": "integer",
"critical": "integer",
"high": "integer",
"medium": "integer",
"low": "integer",
"categories": "object"
},
"timestamp": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/yara/scan/550e8400-e29b-41d4-a716-446655440000"Response
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"matches": [
{
"match_id": 12345,
"rule_name": "cryptominer_coinhive",
"pattern_name": "CoinHive Cryptominer",
"category": "cryptominer",
"severity": "high",
"confidence": 1.0,
"description": "Detects CoinHive cryptocurrency mining code",
"threat_names": ["CoinHive", "Cryptominer"],
"cve_ids": [],
"mitre_techniques": ["T1496"],
"intel_references": ["https://..."],
"matched_strings": ["CoinHive.Anonymous", "cryptonight"],
"match_count": 3,
"tags": ["cryptominer", "browser-mining"],
"detected_at": "2025-01-07T14:23:00Z"
}
],
"summary": {
"total_matches": 2,
"critical": 0,
"high": 1,
"medium": 1,
"low": 0,
"categories": {
"cryptominer": 1,
"webskimmer": 1
}
},
"timestamp": "2025-01-07T15:30:00.000Z"
}/api/v1/yara/{scan_id}YARA Matches (Legacy Endpoint)
Legacy alias for /api/v1/yara/scan/{scan_id}. Returns the same YARA malware pattern matches. Use the /scan/{scan_id} endpoint instead.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
Response
{
"scan_id": "string",
"matches": "array of match objects",
"summary": "object with counts by severity",
"timestamp": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/yara/550e8400-e29b-41d4-a716-446655440000"Response
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"matches": [...],
"summary": {...},
"timestamp": "2025-01-07T15:30:00.000Z"
}/api/v1/registrar/search/{registrar_name}Search Scans by Registrar
Find all scans from domains registered with a specific registrar. Uses fuzzy ILIKE matching for flexible searches. Results include domain, registrar, and scan metadata.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
registrar_name | string | Required | Registrar name (partial match supported) |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Results per page (1-100, default: 20) |
Response
{
"registrar_query": "string",
"total": "integer",
"page": "integer",
"limit": "integer",
"results": "array of scan objects",
"pagination": {
"total": "integer",
"page": "integer",
"limit": "integer",
"total_pages": "integer",
"has_next": "boolean",
"has_prev": "boolean"
}
}Example
Request
curl "https://scanmalware.com/api/v1/registrar/search/GoDaddy?page=1&limit=20"Response
{
"registrar_query": "GoDaddy",
"total": 234,
"page": 1,
"limit": 20,
"results": [
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"url": "https://example.com",
"domain": "example.com",
"title": "Example Domain",
"status": "completed",
"asn": "AS13335",
"submitted_at": "2025-01-07T14:23:00Z",
"screenshot_thumbnail": "https://..."
}
],
"pagination": {
"total": 234,
"page": 1,
"limit": 20,
"total_pages": 12,
"has_next": true,
"has_prev": false
}
}/api/v1/tracking-keys/stats/topTop Tracking Keys Statistics
Get the most commonly used tracking keys by usage count. Includes Google Analytics, Facebook Pixel, and other privacy trackers. Optional filtering by tracker type.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
tracker_type | string | Optional | Filter by tracker type (e.g., "google_analytics", "facebook_pixel") |
limit | integer | Optional | Number of results (1-100, default: 20) |
Response
{
"tracker_type_filter": "string or null",
"limit": "integer",
"total_results": "integer",
"results": "array of tracking key objects with usage statistics"
}Example
Request
curl "https://scanmalware.com/api/v1/tracking-keys/stats/top?tracker_type=google_analytics&limit=10"Response
{
"tracker_type_filter": "google_analytics",
"limit": 10,
"total_results": 10,
"results": [
{
"tracker_type": "google_analytics",
"tracking_key": "UA-12345678-1",
"tracker_name": "Google Analytics (UA)",
"category": "analytics",
"site_count": 1234,
"first_seen": "2023-05-12T08:30:00Z",
"last_seen": "2025-01-07T14:23:00Z"
}
]
}/api/v1/tracking-keys/by-scan/{scan_id}Tracking Keys for Scan
Get all tracking keys detected in a specific scan with usage statistics. Groups results by category and risk level.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
Response
{
"scan_id": "string",
"total_keys": "integer",
"total_unique_trackers": "integer",
"tracking_keys": "array of tracking key objects",
"by_category": "object with counts per category",
"has_high_risk": "boolean",
"has_medium_risk": "boolean"
}Example
Request
curl "https://scanmalware.com/api/v1/tracking-keys/by-scan/550e8400-e29b-41d4-a716-446655440000"Response
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"total_keys": 5,
"total_unique_trackers": 3,
"tracking_keys": [
{
"tracker_type": "google_analytics",
"tracker_name": "Google Analytics (UA)",
"tracking_key": "UA-12345678-1",
"category": "analytics",
"risk_level": "medium",
"detected_url": "https://www.google-analytics.com/analytics.js",
"site_count": 1234,
"first_seen": "2023-05-12T08:30:00Z",
"last_seen": "2025-01-07T14:23:00Z"
}
],
"by_category": {
"analytics": 2,
"advertising": 2,
"social": 1
},
"has_high_risk": false,
"has_medium_risk": true
}/api/v1/tracking-keys/{tracker_type}/{key}Search Scans by Tracking Key
Find all public scans using a specific tracking key. Useful for tracking the spread of specific analytics IDs, pixels, or other identifiers across websites.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
tracker_type | string | Required | Tracker type (e.g., "google_analytics", "facebook_pixel") |
key | string | Required | The tracking key/ID to search for |
page | integer | Optional | Page number (default: 1) |
limit | integer | Optional | Results per page (1-100, default: 20) |
sort | string | Optional | Sort order: "latest" or "oldest" (default: "latest") |
Response
{
"tracker_type": "string",
"tracker_key": "string",
"metadata": "object with tracker info",
"results": "array of scan objects",
"pagination": "object with pagination info"
}Example
Request
curl "https://scanmalware.com/api/v1/tracking-keys/google_analytics/UA-12345678-1?page=1&limit=20"Response
{
"tracker_type": "google_analytics",
"tracker_key": "UA-12345678-1",
"metadata": {
"tracker_name": "Google Analytics (UA)",
"category": "analytics",
"risk_level": "medium",
"site_count": 1234,
"first_seen": "2023-05-12T08:30:00Z",
"last_seen": "2025-01-07T14:23:00Z"
},
"results": [
{
"scan_id": "550e8400-e29b-41d4-a716-446655440000",
"url": "https://example.com",
"final_url": "https://example.com/",
"title": "Example Site",
"submitted_at": "2025-01-07T14:23:00Z",
"detected_url": "https://www.google-analytics.com/analytics.js"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total_items": 1234,
"total_pages": 62,
"has_next": true,
"has_prev": false
}
}/api/v1/netlog/{scan_id}Chrome Network Debug Log
Download Chrome net-log for detailed network-level debugging. Provides raw Chrome network log JSON with DNS lookups, socket connections, HTTP transactions, SSL handshakes, and more.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
Response
{
"content": "Raw JSON network log (application/json)",
"headers": {
"Content-Disposition": "attachment; filename=netlog_{scan_id}.json"
}
}Example
Request
curl "https://scanmalware.com/api/v1/netlog/550e8400-e29b-41d4-a716-446655440000" -o netlog.jsonResponse
{
"constants": {
"logFormatVersion": 1,
"clientInfo": {
"numericVersion": "12800256",
"command_line": "..."
}
},
"events": [
{
"params": {
"source_dependency": {"id": 123, "type": "URL_REQUEST"}
},
"phase": 0,
"source": {"id": 456, "type": "HTTP_STREAM_JOB"},
"time": "123456789",
"type": "HTTP_TRANSACTION_SEND_REQUEST"
}
]
}/api/v1/ns/{nameserver}Nameserver Domain Lookup
Search for all domains using a specific nameserver. Combines two data sources for maximum coverage: a primary zone-file dataset and a supplementary dataset of scanned domains with RDAP/WHOIS/DNS data. If the primary source returns fewer than 10 domains, the supplementary source is queried and unique domains are merged in. Args: nameserver: Nameserver to search for (e.g., "ns1.example.com") limit: Maximum results to return (default: 20, max: 1000) offset: Pagination offset (default: 0) index: Dataset to query ("latest", "ns_lookup", "zones", or specific dataset name) Returns: JSON with domains, metadata, and query stats. When supplementary data is merged, extra fields indicate how many domains were added. Raises: HTTPException: If both data sources fail
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
nameserver | string | Required | |
limit | integer | Optional | |
offset | integer | Optional | |
index | string | Optional |
Response
{
"nameserver": "string",
"total": "integer",
"domains": "array of domain strings",
"limit": "integer",
"offset": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/ns/ns1.cloudflare.com?limit=50"Response
{
"nameserver": "ns1.cloudflare.com",
"total": 15234,
"domains": [
"example.com",
"example.org",
"example.net"
],
"limit": 50,
"offset": 0
}/api/v1/Root
API root endpoint
Example
Request
curl "https://scanmalware.com/api/v1/"Response
{
"name": "ScanMalware API",
"version": "1.0.0",
"status": "online",
"endpoints": {
"scan": "/api/v1/scan",
"bulk_scan": "/api/v1/scan/bulk",
"result": "/api/v1/result/{scan_id}",
"summary": "/api/v1/scan/{scan_id}/summary",
"recent": "/api/v1/recent",
"search": "/api/v1/search",
"batch_status": "/api/v1/scan/batch/{batch_id}",
"status_batch": "/api/v1/scan/status/batch",
"domain_scans": "/api/v1/domains/{domain}/scans",
"stats": "/api/v1/stats",
"screenshot": "/api/v1/screenshot/{scan_id}",
"screenshot_search": "/api/v1/screenshot/search",
"screenshot_duplicates": "/api/v1/screenshot/duplicates",
"screenshot_stats": "/api/v1/screenshot/stats",
"favicon_search": "/api/v1/favicon/search/{mmh3_hash}",
"favicon_stats": "/api/v1/favicon/stats",
"health": "/api/v1/health"
},
"features": [
"Single URL scanning",
"Bulk/batch scanning",
"HTTP transaction analysis",
"Redirect chain detection",
"Security verdict scoring",
"SSL/TLS certificate analysis",
"Tracker detection & analytics",
"Technology fingerprinting",
"Domain-based scan history",
"Comprehensive screenshot hashing (6 algorithms)",
"Reverse image search & similarity detection",
"Duplicate screenshot detection",
"Favicon MMH3 hashing & search",
"Website clustering by favicon",
"Webhook notifications (planned)"
]
}/api/v1/modules/pingHealth Check
Basic health check endpoint - No authentication required Returns simple status for uptime monitoring
Example
Request
curl "https://scanmalware.com/api/v1/modules/ping"Response
{
"status": "ok",
"service": "module_monitoring",
"timestamp": "2026-05-05T11:10:31.456131+00:00"
}/api/v1/rssGet Rss Feed
RSS feed of latest public scans (cached for 60 seconds)
Example
Request
curl "https://scanmalware.com/api/v1/rss"Response
<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:ns0="http://www.w3.org/2005/Atom" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title>ScanMalware.com - Latest Scans</title><link>https://scanmalware.com</link><description>Latest public URL security scans from ScanMalware.com</description><language>en-us</language><ns0:link href="https://scanmalware.com/api/v1/rss" rel="self" type="application/rss+xml" /><item><title>🟢 https://perso.pbandai-glb.com</title><link>https://scanmalware.com/result/1999d08c-d374-4ecc-98d0-da2db2c22a96</link><guid isPermaLink="true">https://scanmalw
... [truncated]/api/v1/og/{scan_id}Get Og Metadata
Get Open Graph metadata for a scan (lightweight endpoint for link previews)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required |
Response
{
"og:title": "string",
"og:description": "string",
"og:url": "string",
"og:type": "string",
"og:site_name": "string",
"og:image": "string",
"og:image:type": "string",
"og:image:width": "string",
"og:image:height": "string",
"og:image:alt": "string",
"twitter:card": "string",
"twitter:title": "string",
"twitter:description": "string",
"twitter:image": "string",
"scan_type": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/og/123e4567-e89b-12d3-a456-426614174000"Response
{
"og:title": "Security Scan: pointdesuture-lesite.com",
"og:description": "✅ Low Risk - https://pointdesuture-lesite-com.pages.dev/css/lib/fonts/slick.html",
"og:url": "https://scanmalware.com/result/123e4567-e89b-12d3-a456-426614174000",
"og:type": "website",
"og:site_name": "ScanMalware.com",
"og:image": "https://scanmalware.com/api/v1/screenshot/123e4567-e89b-12d3-a456-426614174000.png?width=1200&format=webp",
"og:image:type": "image/webp",
"og:image:width": "1200",
"og:image:height": "620",
"og:image:alt": "Screenshot of https://pointdesuture-lesite-com.pages.dev/css/lib/fonts/slick.html",
"twitter:card": "summary_large_image",
"twitter:title": "Security Scan: pointdesuture-lesite.com",
"twitter:description": "✅ Low Risk - https://pointdesuture-lesite-com.pages.dev/css/lib/fonts/slick.html",
"twitter:image": "https://scanmalware.com/api/v1/screenshot/123e4567-e89b-12d3-a456-426614174000.png?width=1200&format=webp",
"scan_type": "public"
}/api/v1/result/{scan_id}/progressGet Scan Progress Endpoint
Get current scan progress for frontend progress bar
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required |
Example
Request
curl "https://scanmalware.com/api/v1/result/123e4567-e89b-12d3-a456-426614174000/progress"Response
{
"current_step": 8,
"total_steps": 8,
"step_name": "Completed",
"percentage": 100,
"status": "completed"
}/api/v1/reports/{scan_id}/countsGet Scan Report Counts
Get vote counts for a specific scan (public endpoint, cached for 60 seconds)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan ID |
Example
Request
curl "https://scanmalware.com/api/v1/reports/123e4567-e89b-12d3-a456-426614174000/counts"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"thumbs_up": 0,
"thumbs_down": 0,
"total": 0
}/api/v1/reportSubmit User Report
Submit a report about a scanned URL Rate Limits: - Maximum {REPORT_RATE_LIMIT_PER_IP} reports per IP per hour - Maximum {REPORT_RATE_LIMIT_PER_SCAN} reports per scan Report types: - positive_feedback: Positive feedback (helpful/accurate scan) - phishing: Phishing website - spam: Spam or unwanted content - counterfeit: Selling counterfeit goods - scam: Scam website - broken_scan: Scan failed or incomplete - malware: Contains malware - illegal_content: Illegal content - copyright: Copyright violation - technical_issue: Technical issue with scan - other: Other issue (provide details)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan ID to report |
report_type | string | Required | |
report_details | string | Optional | Additional details, especially for 'other' category |
captcha_answer | string | Optional | Captcha answer |
captcha_token | string | Optional | Captcha token |
skip_captcha | string | Optional | Skip captcha for positive feedback |
voter_token | string | Optional | Random per-browser id sent with Mark as Safe / Mark as Malicious, so a vote can be changed |
Response
{
"status": "string",
"report_id": "integer",
"scan_id": "string"
}Example
Request
curl -X POST "https://scanmalware.com/api/v1/report" \
-H "Content-Type: application/json" \
-d '{"scan_id": "123e4567-e89b-12d3-a456-426614174000", "report_type": "phishing", "description": "Spoofed login page targeting Microsoft accounts"}'Response
{
"status": "ok",
"report_id": 4827,
"scan_id": "123e4567-e89b-12d3-a456-426614174000"
}/api/v1/scan-statisticsGet Scan Statistics
Get pre-computed scan statistics. Returns comprehensive scan statistics including: - Total scans and breakdown by status - Scans by type (public/private/api) - Time-based counts (24h, 7d, 30d) - Last updated timestamp
Example
Request
curl "https://scanmalware.com/api/v1/scan-statistics"Response
{
"total_scans": 331968,
"completed_scans": 302491,
"pending_scans": 0,
"processing_scans": 1,
"failed_scans": 2865,
"public_scans": 331703,
"private_scans": 35,
"api_scans": 0,
"scans_last_24h": 1494,
"scans_last_7d": 10733,
"scans_last_30d": 44830,
"last_updated": "2026-03-26T10:15:02.024833+00:00",
"completion_rate": 91.12,
"failure_rate": 0.86,
"data_age_seconds": 3459322,
"data_age_minutes": 57655.4
}/api/v1/scan-statistics/quickGet Quick Stats
Get ultra-fast overview statistics. Performance: Sub-millisecond response time Returns only the most essential counts for dashboard overview.
Example
Request
curl "https://scanmalware.com/api/v1/scan-statistics/quick"Response
{
"total_scans": 331968,
"completed_scans": 302491,
"scans_last_24h": 1494,
"last_updated": "2026-03-26T10:15:02.024833+00:00"
}/api/v1/scan-statistics/dashboardGet Dashboard Stats
Get comprehensive statistics optimized for dashboard display. Returns all statistics in a dashboard-friendly format with computed percentages, rates, and time-based breakdowns.
Example
Request
curl "https://scanmalware.com/api/v1/scan-statistics/dashboard"Response
{
"overview": {
"total_scans": 331968,
"completed_scans": 302491,
"completion_rate_pct": 91.12,
"last_updated": "2026-03-26T10:15:02.024833+00:00"
},
"by_status": {
"completed": 302491,
"pending": 0,
"processing": 1,
"failed": 2865
},
"by_type": {
"public": 331703,
"private": 35,
"api": 0
},
"time_periods": {
"last_24h": 1494,
"last_7d": 10733,
"last_30d": 44830,
"older_than_30d": 287138
},
"rates": {
"avg_per_day_last_7d": 1533.3,
"avg_per_day_last_30d": 1494.3,
"failure_rate_pct": 0.86
},
"metadata": {
"data_updated_at": "2026-03-26T10:15:02.024833+00:00",
"refresh_interval": "hourly (at :15)"
}
}/api/v1/scan-statistics/by-statusGet Stats By Status
Get scan counts grouped by status. Returns breakdown of scans by their current status (completed, pending, processing, failed).
Example
Request
curl "https://scanmalware.com/api/v1/scan-statistics/by-status"Response
{
"completed_scans": 302491,
"pending_scans": 0,
"processing_scans": 1,
"failed_scans": 2865,
"total_scans": 331968,
"completed_pct": 91.12,
"pending_pct": 0.0,
"processing_pct": 0.0,
"failed_pct": 0.86
}/api/v1/scan-statistics/by-typeGet Stats By Type
Get scan counts grouped by type. Returns breakdown of scans by type (public, private, api).
Example
Request
curl "https://scanmalware.com/api/v1/scan-statistics/by-type"Response
{
"public_scans": 331703,
"private_scans": 35,
"api_scans": 0,
"total_scans": 331968,
"public_pct": 99.92,
"private_pct": 0.01,
"api_pct": 0.0
}/api/v1/scan-statistics/time-periodsGet Stats By Time
Get scan counts by time period. Returns counts for different time windows (24 hours, 7 days, 30 days) and total.
Example
Request
curl "https://scanmalware.com/api/v1/scan-statistics/time-periods"Response
{
"scans_last_24h": 1494,
"scans_last_7d": 10733,
"scans_last_30d": 44830,
"total_scans": 331968,
"scans_last_7d_excl_24h": 9239,
"scans_last_30d_excl_7d": 34097,
"scans_older_than_30d": 287138,
"avg_per_day_last_24h": 1494,
"avg_per_day_last_7d": 1533.3,
"avg_per_day_last_30d": 1494.3
}/api/v1/stats/capabilities/latestGet Latest Capabilities
Get latest detection capabilities report from JSONL file
Example
Request
curl "https://scanmalware.com/api/v1/stats/capabilities/latest"Response
{
"date": "2026-05-05",
"generated_at": "2026-05-05T05:00:07.702066Z",
"detection_capabilities": {
"ioc_indicators": 3013559,
"malware_detection_rules": 82126,
"clamav_signatures": 3642553,
"total": 6738238
},
"breakdown": {
"ioc_indicators": {
"maltrail_ips": 41744,
"maltrail_domains": 1562567,
"threatfox": 154168,
"malware_report": 4488,
"misp": 1250592
},
"malware_detection_rules": {
"yara_rules": 32078,
"yara_repositories": 12,
"suricata_ids_rules": 50032,
"db_malware_patterns": 16
},
"clamav_signatures": {
"total": 3642553,
"version": "27991"
}
}
}/api/v1/stats/capabilities/by-dateGet Capabilities By Date
Get detection capabilities for a specific date, or nearest date if no exact match
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_date | string | Required | Scan date in YYYY-MM-DD format |
Example
Request
curl "https://scanmalware.com/api/v1/stats/capabilities/by-date?scan_date=2026-05-01"Response
{
"date": "2026-05-01",
"generated_at": "2026-05-01T05:00:07.439885Z",
"detection_capabilities": {
"ioc_indicators": 2999404,
"malware_detection_rules": 82027,
"clamav_signatures": 3642543,
"total": 6723974
},
"breakdown": {
"ioc_indicators": {
"maltrail_ips": 40623,
"maltrail_domains": 1560575,
"threatfox": 152727,
"malware_report": 4488,
"misp": 1240991
},
"malware_detection_rules": {
"yara_rules": 32078,
"yara_repositories": 12,
"suricata_ids_rules": 49933,
"db_malware_patterns": 16
},
"clamav_signatures": {
"total": 3642543,
"version": "27987"
}
},
"matched": "exact"
}/api/v1/search/smqlSmql Search
Search scans using the ScanMalware Query Language (SMQL). Syntax examples: - Simple text: `paypal login` - Filters: `domain:paypal.com`, `country:RU`, `technology:WordPress` - Boolean: `technology:WordPress AND country:RU` - Negation: `-domain:google.com` or `NOT domain:google.com` - Grouping: `(technology:WordPress OR technology:Joomla) AND country:CN` - Ranges: `js_risk_score:60..100`, `submitted:last7d` - Existence: `has:malware`, `has:pastejacking`
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
q | string | Required | SMQL query string |
page | integer | Optional | Page number |
limit | integer | Optional | Results per page |
sort | string | Optional | Sort order: newest, oldest, url, load_time, ip_count |
Example
Request
curl "https://scanmalware.com/api/v1/search/smql?q=domain%3Apaypal.com&limit=3"Response
{
"query": "domain:paypal.com",
"results": [
{
"scan_id": "d5f86fff-dc37-4561-89db-bab413dc7f88",
"url": "https://www.paypal.com/ncp/payment/VZ3GQBXNTS4MW",
"final_url": "https://www.paypal.com/ncp/payment/VZ3GQBXNTS4MW",
"title": "PayPal",
"status": "completed",
"submitted_at": "2026-04-27T17:01:48.541854",
"completed_at": "2026-04-27T17:03:01.588138",
"screenshot_url": "/api/v1/screenshot/d5f86fff-dc37-4561-89db-bab413dc7f88.png",
"primary_asn": null,
"asn_names": [
"Google LLC",
"Cloudflare, Inc.",
"Fastly, Inc."
],
"countries": [
"US",
"DE"
],
"ip_count": 5,
"load_time": 4.335993051528931
},
{
"scan_id": "25ddef90-e2c5-47df-bae4-2c06e40fbbc2",
"url": "https://paylalo.sviluppo.host/ge/DUVzTTavlOw/?redirection=login",
"final_url": "https://www.paypal.com/de/home",
"title": "PayPal Konto | Digitale Mobile Wallet | PayPal DE",
"status": "completed",
"submitted_at": "2026-04-26T15:27:21.335598",
"completed_at": "2026-04-26T15:28:18.536785",
"screenshot_url": "/api/v1/screenshot/25ddef90-e2c5-47df-bae4-2c06e40fbbc2.png",
"primary_asn": null,
"asn_names": [
"Google LLC",
"Host SpA",
"Cloudflare, Inc."
],
"countries": [
"IT",
"US"
],
"ip_count": 12,
"load_time": 4.966224670410156
},
// ... truncated ...
}/api/v1/search/smql/filtersSmql Filters
Return all available SMQL filters grouped by category.
Example
Request
curl "https://scanmalware.com/api/v1/search/smql/filters"Response
{"filters":{"Core":[{"name":"url","type":"text","description":"URL (fuzzy match with trigram similarity)","store":"pg","examples":["paypal.com","*.bank.com","http://example.com"],"supports_comparison":false,"supports_wildcard":true,"supports_range":false,"enum_values":null},{"name":"domain","type":"text","description":"Extracted domain name","store":"pg","examples":["paypal.com","example.org"],"supports_comparison":false,"supports_wildcard":true,"supports_range":false,"enum_values":null},{"name":"title","type":"text","description":"Page title (substring match)","store":"pg","examples":["login"
... [truncated]/api/v1/search/smql/statsSmql Stats
Return estimated total public scan count (from pg_class, essentially free).
Example
Request
curl "https://scanmalware.com/api/v1/search/smql/stats"Response
{
"total_scans": 387647
}/api/v1/search/ip/{ip_address}/statsGet Ip Stats
Get detailed statistics and enrichment data for an IP address
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
ip_address | string | Required | IP address to get statistics for |
page | integer | Optional | Page number |
limit | integer | Optional | Items per page |
Example
Request
curl "https://scanmalware.com/api/v1/search/ip/93.184.216.34/stats"Response
{
"ip_address": "93.184.216.34",
"total_scans": 0,
"unique_urls": 0,
"first_seen": null,
"last_seen": null,
"geoip": null,
"asn": null,
"asn_org": null,
"country": null,
"city": null,
"state": null,
"bgp_data": null,
"dns_data": {
"domains": [
{
"domain": "clinical-uat.prod.rxrx.io",
"root": "rxrx.io",
"type": "A",
"ips": [
"93.184.216.34"
],
"timestamp": 1777978516
},
{
"domain": "iw-db-api.prod.rxrx.io",
"root": "rxrx.io",
"type": "A",
"ips": [
"93.184.216.34"
],
"timestamp": 1777975796
},
{
"domain": "grafana.rxrx.io",
"root": "rxrx.io",
"type": "A",
"ips": [
"93.184.216.34"
],
"timestamp": 1777975015
},
{
"domain": "inception-docs.prod.rxrx.io",
"root": "rxrx.io",
"type": "A",
"ips": [
"93.184.216.34"
],
"timestamp": 1777974088
},
{
"domain": "inference.rxrx.io",
"root": "rxrx.io",
"type": "A",
"ips": [
"93.184.216.34"
],
"timestamp": 1777970663
},
{
"domain": "inference.exs.rxrx.io",
"root": "rxrx.io",
"type": "A",
"ips": [
"93.184.216.34"
],
"timestamp": 1777970663
},
// ... truncated ...
}/api/v1/technologies/bot-protection/{scan_id}Get Bot Protection
Get bot protection technologies detected in a specific scan
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required |
Example
Request
curl "https://scanmalware.com/api/v1/technologies/bot-protection/123e4567-e89b-12d3-a456-426614174000"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"bot_protection": [
{
"name": "Cloudflare Bot Management",
"version": null,
"category": "wappalyzer",
"confidence": 55,
"detected_at": "2026-05-05T11:03:09.705276",
"website": null,
"description": null,
"details": {
"cpe": null,
"source": "wappalyzer",
"implies": [
"Cloudflare"
],
"detected_by": [
"headers",
"cookies"
],
"detection_details": [
{
"method": "headers",
"matches": [
{
"type": "presence",
"value": "9f6f3d09784adbc8-FRA",
"header": "cf-ray"
}
]
},
{
"method": "cookies",
"matches": [
{
"name": "cf_clearance",
"exists": true
}
]
}
],
"confidence_breakdown": {
"cookies": 15,
"headers": 40
}
}
}
],
"detected": true
}/api/v1/rpki/{scan_id}Get Rpki Validation
Get RPKI validation results for a scan. Returns validation status (valid/invalid/not-found) for each server IP address, with ASN, covering prefix, and risk contribution.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required |
Response
objectExample
Request
curl "https://scanmalware.com/api/v1/rpki/123e4567-e89b-12d3-a456-426614174000"Response
{
"validations": [
{
"ip": "23.36.162.198",
"asn": 20940,
"as_name": "Akamai International B.V.",
"covering_prefix": "23.36.162.0/24",
"rpki_status": "valid",
"risk_contribution": 0
},
{
"ip": "23.36.162.215",
"asn": 20940,
"as_name": "Akamai International B.V.",
"covering_prefix": "23.36.162.0/24",
"rpki_status": "valid",
"risk_contribution": 0
},
{
"ip": "54.201.178.167",
"asn": 16509,
"as_name": "Amazon.com, Inc.",
"covering_prefix": "54.200.0.0/15",
"rpki_status": "valid",
"risk_contribution": 0
},
{
"ip": "104.16.79.73",
"asn": 13335,
"as_name": "Cloudflare, Inc.",
"covering_prefix": "104.16.64.0/20",
"rpki_status": "valid",
"risk_contribution": 0
},
{
"ip": "104.17.71.73",
"asn": 13335,
"as_name": "Cloudflare, Inc.",
"covering_prefix": "104.17.64.0/20",
"rpki_status": "valid",
"risk_contribution": 0
},
{
"ip": "104.17.162.123",
"asn": 13335,
"as_name": "Cloudflare, Inc.",
"covering_prefix": "104.17.160.0/20",
"rpki_status": "valid",
"risk_contribution": 0
},
{
"ip": "104.17.163.123",
"asn": 13335,
"as_name": "Cloudflare, Inc.",
"covering_prefix": "104.17.160.0/20",
"rpki_status": "valid",
"risk_contribution": 0
},
{
"ip": "104.17.164.123",
// ... truncated ...
}/api/v1/segments/{segment_id}Get Segment
Get basic information about a JavaScript segment. Args: segment_id: The unique segment identifier Returns: Segment metadata including script URL, function name, code length, etc.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
segment_id | integer | Required | JavaScript segment ID |
Example
Request
curl "https://scanmalware.com/api/v1/segments/1"Response
{
"segment_id": 1,
"scan_id": "62a873c0-665d-47e9-9da9-e680dc9f8929",
"code_hash": "37b81c419f93d275bdcaa346d8f33121fda747c61a7eb8fa754760bbd95d364e",
"tlsh_hash": null,
"script_url": "(inline)",
"function_name": null,
"code_length": 102,
"code_snippet": "(() => {\n Object.defineProperty(navigator, 'webdriver', {\n get: () => undefined\n });\n })()",
"risk_score": 0,
"risk_factors": [],
"library_match": null,
"patterns": {
"entropy": 4.403796210347942,
"hasEval": false,
"hasBase64": false,
"hasWindow": false,
"codeLength": 102,
"hexEscapes": 0,
"hasDocument": false,
"hasUnescape": false,
"hasNavigator": false,
"octalEscapes": 0,
"hasCharCodeAt": false,
"unicodeEscapes": 0,
"bracketNotation": 0,
"suspiciousVarNames": 0,
"stringConcatenation": 0,
"hasFunctionConstructor": false
}
}/api/v1/segments/{segment_id}/securityGet Segment Security
Get security analysis for a specific JavaScript segment: malware pattern matches (YARA and custom patterns), risk score and severity, pattern descriptions and recommendations, and threat categories. To get this for every segment of a scan, use /api/v1/segments/by-scan/{scan_id}/security instead — one request rather than one per segment, and far cheaper to serve.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
segment_id | integer | Required | JavaScript segment ID |
Example
Request
curl "https://scanmalware.com/api/v1/segments/1/security"Response
{
"segment_id": 1,
"scan_id": "62a873c0-665d-47e9-9da9-e680dc9f8929",
"script_url": "(inline)",
"function_name": null,
"code_length": 102,
"security": {
"risk_score": 0,
"severity": "NONE",
"total_matches": 0,
"average_confidence": 0,
"threat_categories": [],
"pattern_matches": [],
"static_risk_score": 0,
"risk_factors": [],
"library_match": null
}
}/api/v1/tls/{scan_id}/certificate/downloadDownload Certificate
Download the TLS/SSL certificate in PEM format Returns the certificate as a downloadable .pem file that can be: - Imported into browsers/keychains - Inspected with OpenSSL (openssl x509 -in cert.pem -text -noout) - Used for verification and analysis Results are cached for 60 seconds (only when data exists).
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required |
Example
Request
curl "https://scanmalware.com/api/v1/tls/123e4567-e89b-12d3-a456-426614174000/certificate/download"Response
-----BEGIN CERTIFICATE-----
MIIDhTCCAwqgAwIBAgISBkRX3ylv/RvcLkTm+bSYyaAaMAoGCCqGSM49BAMDMDIx
CzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1MZXQncyBFbmNyeXB0MQswCQYDVQQDEwJF
NzAeFw0yNjAzMTAxMDQ2MTZaFw0yNjA2MDgxMDQ2MTVaMBcxFTATBgNVBAMTDHd3
dy5odXNkLm9yZzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABNjJpke7lPyTGbOa
KG6WP8Bu8+FSWIEesCwxFksImmrCM5bXnwFzKyNzMazLYG6C1jhJ0T7RD3y+hKCy
8PI4wCmjggIZMIICFTAOBgNVHQ8BAf8EBAMCB4AwEwYDVR0lBAwwCgYIKwYBBQUH
AwEwDAYDVR0TAQH/BAIwADAdBgNVHQ4EFgQUstNgPWN3xfmbAVsGDr031koaeqAw
HwYDVR0jBBgwFoAUrkie3IcdRKBv2qLlYHQEeMKcAIAwMgYIKwYBBQUHAQEEJjAk
MCIGCCsGAQUFBzAChhZodHRwOi8vZTcuaS5sZW5jci5vcmcvMBcG
... [truncated]/api/v1/screenshot/{scan_id}Screenshot Metadata (HEAD)
Issue a HEAD request to fetch screenshot metadata (Content-Type, Content-Length) without downloading the PNG body. Useful for cheaply checking whether a screenshot exists for a given scan.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | |
width | integer | Optional | Resize width (maintains aspect ratio) |
height | integer | Optional | Resize height (maintains aspect ratio) |
format | string | Optional | Output format: png or webp |
Response
Empty body; status 200 if the screenshot exists, 404 if not.Example
Request
curl -I "https://scanmalware.com/api/v1/screenshot/123e4567-e89b-12d3-a456-426614174000"Response
HTTP/2 200
content-type: image/png
content-length: 19049
cache-control: public, max-age=86400/api/v1/js-fingerprinter2/{scan_id}Get Js Fingerprinter2 Results
Get JavaScript obfuscation detection results for a specific scan. Returns: Obfuscation analysis results including risk level, eval calls, and high-risk events Note: By default, detailed_events is excluded as it can be 10MB+ in size. Use ?include_detailed_events=true to include it.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID to retrieve obfuscation detection results for |
include_detailed_events | boolean | Optional | Include detailed_events field (can be very large, 10MB+) |
Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/123e4567-e89b-12d3-a456-426614174000"Response
{"scan_id":"123e4567-e89b-12d3-a456-426614174000","session_id":"session_1777978988437_u07bjp2ew","target_url":"https://www.husd.org/","scan_url":"https://husd.org","overall_risk":"critical","max_risk_score":100,"average_risk_score":85.67,"total_scripts":454,"eval_calls":0,"function_constructor_calls":4,"high_risk_events_count":3,"high_risk_events":[{"type":"static_analysis","score":95,"urlId":"u0","factors":["charcode_manipulation","excessive_concatenation","bracket_notation_abuse","excessive_escapes","high_entropy","suspicious_variable_names"],"timestamp":1777978991039,"codeSnippet":"/*! jQue
... [truncated]/api/v1/js-fingerprinter2/{scan_id}/scriptsGet Js Fingerprinter2 Per Script
Get per-script behavioral fingerprint data from js_fingerprinter2. Aggregates detailed_events by script URL to provide per-script summaries of eval calls, Function constructor usage, risk scores, and obfuscation patterns. Returns: Dictionary keyed by script URL (or "(inline)") with behavioral summary per script.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID to retrieve per-script behavioral data for |
Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/123e4567-e89b-12d3-a456-426614174000/scripts"Response
{"scripts":{"u11":{"evalCalls":0,"functionCalls":0,"staticAnalyses":0,"exceptions":0,"maxRiskScore":0,"avgRiskScore":0,"patterns":[],"codeHash":null},"(inline)":{"evalCalls":0,"functionCalls":0,"staticAnalyses":56,"exceptions":0,"maxRiskScore":25,"avgRiskScore":11.6,"patterns":[{"entropy":4.403796210347942,"hasEval":false,"hasBase64":false,"hasWindow":false,"codeLength":102,"hexEscapes":0,"hasDocument":false,"hasUnescape":false,"hasNavigator":false,"octalEscapes":0,"hasCharCodeAt":false,"unicodeEscapes":0,"bracketNotation":0,"suspiciousVarNames":0,"stringConcatenation":0,"hasFunctionConstructo
... [truncated]/api/v1/js-fingerprinter2/statsGet Js Fingerprinter2 Stats
Get aggregate statistics for obfuscation detection across all scans. Returns: Summary statistics including total scans analyzed, risk distribution, common patterns
Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/stats"Response
{
"total_analyzed": 278741,
"risk_distribution": {
"critical": 97033,
"high": 12171,
"medium": 8290,
"low": 157759
},
"averages": {
"max_risk_score": 39.57,
"avg_risk_score": 32.2,
"scripts_per_scan": 137.53
},
"totals": {
"eval_calls": 1269858,
"function_constructor_calls": 1080534,
"high_risk_events": 536230
},
"last_analysis_at": "2026-05-05T11:08:39.049652+00:00"
}/api/v1/js-fingerprinter2/search/js-obfuscationSearch Js Obfuscation
Search for scans with JavaScript obfuscation patterns. NOTE: This endpoint has been moved to /api/v1/search/js-obfuscation for consistency. Please use the new endpoint instead.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
risk_level | string | Optional | Filter by risk level: low, medium, high, critical |
min_risk_score | integer | Optional | Minimum risk score |
has_eval | boolean | Optional | Filter scans with eval() calls |
limit | integer | Optional |
Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinter2/search/js-obfuscation"Response
{"total":20,"filters":{"risk_level":null,"min_risk_score":null,"has_eval":null},"results":[{"scan_id":"92dd3cd3-464b-4c5b-88f4-cbffea1cfff2","url":"https://theearthlingco.com","target_url":null,"overall_risk":null,"max_risk_score":null,"average_risk_score":0,"total_scripts":null,"eval_calls":null,"function_constructor_calls":null,"high_risk_events_count":null,"screenshot_thumbnail":"/api/v1/screenshot/92dd3cd3-464b-4c5b-88f4-cbffea1cfff2.png","analyzed_at":"2026-05-04T21:08:19.096272+00:00","submitted_at":"2026-05-04T21:06:14.858115"},{"scan_id":"3e34e760-2606-4543-8
... [truncated]/api/v1/jsfingerprint/hash/sha256/{hash}Search By Sha256
Find exact JavaScript content matches by SHA-256 hash. Use Case: Malware detection, code reuse tracking, supply chain security Performance: < 100ms (indexed lookup)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash | string | Required | SHA-256 hash (64 hex characters) |
include_scans | boolean | Optional | Include scan references |
limit | integer | Optional | Max results |
from_date | string | Optional | Start date (ISO 8601) |
to_date | string | Optional | End date (ISO 8601) |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/hash/sha256/3f08ccfa3fe55172d853efc9d5673dffa359873e6199f8175d9ca853b3924857?limit=3"Response
{
"hash_type": "sha256",
"hash_value": "3f08ccfa3fe55172d853efc9d5673dffa359873e6199f8175d9ca853b3924857",
"total_matches": 1,
"unique_scans": 1,
"first_seen": "2026-05-05T11:03:25.735908Z",
"last_seen": "2026-05-05T11:03:25.735908Z",
"prevalence": "rare",
"date_range": {
"from": null,
"to": null
},
"matches": [
{
"fingerprint_id": 5037368,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://www.husd.org/uploaded/themes/default_24/main.js?1763056584",
"code_length": 33725,
"function_count": 195,
"library_detected": null,
"library_version": null,
"is_bundled": null,
"bundler_type": null,
"is_cdn": false,
"cdn_type": null,
"obfuscation_score": null,
"created_at": "2026-05-05T11:03:25.735908Z"
}
],
"matches_truncated": false,
"performance": {
"query_time_note": "< 100ms typical",
"index_used": "idx_fp_content_hash"
}
}/api/v1/jsfingerprint/hash/md5/{hash}Search By Md5
Find exact JavaScript content matches by MD5 hash. Use Case: Legacy hash lookups, malware detection, code reuse tracking Performance: < 100ms (indexed lookup)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash | string | Required | MD5 hash (32 hex characters) |
include_scans | boolean | Optional | Include scan references |
limit | integer | Optional | Max results |
from_date | string | Optional | Start date (ISO 8601) |
to_date | string | Optional | End date (ISO 8601) |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/hash/md5/ca4877aaea6ea720336eaefcd4234c20?limit=3"Response
{
"hash_type": "md5",
"hash_value": "ca4877aaea6ea720336eaefcd4234c20",
"total_matches": 1,
"unique_scans": 1,
"first_seen": "2026-05-05T11:03:25.735908Z",
"last_seen": "2026-05-05T11:03:25.735908Z",
"prevalence": "rare",
"date_range": {
"from": null,
"to": null
},
"matches": [
{
"fingerprint_id": 5037368,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://www.husd.org/uploaded/themes/default_24/main.js?1763056584",
"code_length": 33725,
"function_count": 195,
"library_detected": null,
"library_version": null,
"is_bundled": null,
"bundler_type": null,
"is_cdn": false,
"cdn_type": null,
"obfuscation_score": null,
"created_at": "2026-05-05T11:03:25.735908Z"
}
],
"matches_truncated": false,
"performance": {
"query_time_note": "< 100ms typical",
"index_used": "idx_fp_content_md5"
}
}/api/v1/jsfingerprint/hash/sha1/{hash}Search By Sha1
Find exact JavaScript content matches by SHA-1 hash. Use Case: Legacy hash lookups, malware detection, code reuse tracking Performance: < 100ms (indexed lookup)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash | string | Required | SHA-1 hash (40 hex characters) |
include_scans | boolean | Optional | Include scan references |
limit | integer | Optional | Max results |
from_date | string | Optional | Start date (ISO 8601) |
to_date | string | Optional | End date (ISO 8601) |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/hash/sha1/1c98781e6979d27fff01627d11123c95c7fb611b?limit=3"Response
{
"hash_type": "sha1",
"hash_value": "1c98781e6979d27fff01627d11123c95c7fb611b",
"total_matches": 1,
"unique_scans": 1,
"first_seen": "2026-05-05T11:03:25.735908Z",
"last_seen": "2026-05-05T11:03:25.735908Z",
"prevalence": "rare",
"date_range": {
"from": null,
"to": null
},
"matches": [
{
"fingerprint_id": 5037368,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://www.husd.org/uploaded/themes/default_24/main.js?1763056584",
"code_length": 33725,
"function_count": 195,
"library_detected": null,
"library_version": null,
"is_bundled": null,
"bundler_type": null,
"is_cdn": false,
"cdn_type": null,
"obfuscation_score": null,
"created_at": "2026-05-05T11:03:25.735908Z"
}
],
"matches_truncated": false,
"performance": {
"query_time_note": "< 100ms typical",
"index_used": "idx_fp_content_sha1"
}
}/api/v1/jsfingerprint/hash/normalized/{hash}Search By Normalized Hash
Find whitespace-independent code matches by normalized hash. Use Case: Detect minified/formatted variants of same code Performance: < 100ms (indexed lookup)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash | string | Required | Normalized hash (64 hex characters) |
include_scans | boolean | Optional | Include scan references |
limit | integer | Optional | Max results |
from_date | string | Optional | Start date (ISO 8601) |
to_date | string | Optional | End date (ISO 8601) |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/hash/normalized/501437d02dc4d96a6e2957c26796d3f6bdd8efd99fae777ceba7dd0a82832117?limit=3"Response
{
"hash_type": "normalized",
"hash_value": "501437d02dc4d96a6e2957c26796d3f6bdd8efd99fae777ceba7dd0a82832117",
"total_matches": 1,
"unique_scans": 1,
"first_seen": "2026-05-05T11:03:25.735908Z",
"last_seen": "2026-05-05T11:03:25.735908Z",
"prevalence": "rare",
"date_range": {
"from": null,
"to": null
},
"matches": [
{
"fingerprint_id": 5037368,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://www.husd.org/uploaded/themes/default_24/main.js?1763056584",
"code_length": 33725,
"function_count": 195,
"library_detected": null,
"library_version": null,
"is_bundled": null,
"bundler_type": null,
"is_cdn": false,
"cdn_type": null,
"obfuscation_score": null,
"created_at": "2026-05-05T11:03:25.735908Z"
}
],
"matches_truncated": false,
"note": "Normalized hash ignores whitespace differences"
}/api/v1/jsfingerprint/hash/fuzzy/{fuzzy_hash}Search By Fuzzy Hash
Find similar code using SSDEEP fuzzy hashing. Use Case: Detect obfuscated/modified variants of malware Performance: 500ms-2s (requires fuzzy comparison) Note: Full SSDEEP comparison requires external library - this endpoint does exact fuzzy_hash matches. For true fuzzy matching, SSDEEP library integration is required.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
fuzzy_hash | string | Required | SSDEEP fuzzy hash |
min_similarity | integer | Optional | Minimum similarity percentage |
limit | integer | Optional | Max results |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/hash/fuzzy/12:adda3838eb7c650774c7b7ba21c497529bdaed20417ea37b7049a3108f3638239d0ce2f45925eda158b255c3377d68063ea991f330eaab4f8512d9b45344b90669fedcd027c31e0ee0a08623d38ceaa4c3839c9c72907a0adfe0e71b26ae0d324840c459bbc77a7e8ce03a8c5ff93542f33931fec101058e4ad35edf69dcd3d9255131e83ba6c276f65d4fbe48a8457e0b27bb72da1ca8f3d923aa33d5aa49a3b72a5b9021c49752a1fa32a14c65d0be728b8100618fb9f679a716adfaee4ca3cf8c1aca2c116e210626e244fa82a989b2e436a0dc32c2f122c1deff18e498ae93cd9c44bffaee77c18198ae617a4046ebb99ea1f3b5dd255421a3ac7547e538?limit=3"Response
{
"hash_type": "fuzzy_ssdeep",
"hash_value": "12:adda3838eb7c650774c7b7ba21c497529bdaed20417ea37b7049a3108f3638239d0ce2f45925eda158b255c3377d68063ea991f330eaab4f8512d9b45344b90669fedcd027c31e0ee0a08623d38ceaa4c3839c9c72907a0adfe0e71b26ae0d324840c459bbc77a7e8ce03a8c5ff93542f33931fec101058e4ad35edf69dcd3d9255131e83ba6c276f65d4fbe48a8457e0b27bb72da1ca8f3d923aa33d5aa49a3b72a5b9021c49752a1fa32a14c65d0be728b8100618fb9f679a716adfaee4ca3cf8c1aca2c116e210626e244fa82a989b2e436a0dc32c2f122c1deff18e498ae93cd9c44bffaee77c18198ae617a4046ebb99ea1f3b5dd255421a3ac7547e538",
"min_similarity": 50,
"total_matches": 1,
"matches": [
{
"fingerprint_id": 5037368,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://www.husd.org/uploaded/themes/default_24/main.js?1763056584",
"code_length": 33725,
"function_count": 195,
"library_detected": null,
"library_version": null,
"is_bundled": null,
"bundler_type": null,
"is_cdn": null,
"cdn_type": null,
"obfuscation_score": null,
"created_at": "2026-05-05T11:03:25.735908Z",
// ... truncated ...
}/api/v1/jsfingerprint/library/{library_name}Search By Library
Find all scripts using a specific JavaScript library. Use Case: Vulnerable library tracking, supply chain security Performance: 500ms-1s
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
library_name | string | Required | Library name (e.g., 'react', 'vue', 'jquery') |
version | string | Optional | Specific version (e.g., '16.13.1') |
version_pattern | string | Optional | Version wildcard (e.g., '16.*') |
min_confidence | number | Optional | Minimum detection confidence |
include_cdn_only | boolean | Optional | Filter to CDN-hosted only |
page | integer | Optional | Page number |
per_page | integer | Optional | Results per page |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/library/jquery"Response
{"library_name":"jquery","version_filter":null,"total_fingerprints":67152,"unique_scans":42300,"unique_urls":51678,"version_breakdown":{"3.7.1":16177,"unknown":8820,"1.13.3":3689,"3.5.1":3131,"3.6.0":3091,"2.2.4":1907,"3.7.0":1891,"1.12.4":1734,"1.11.3":1645,"1.12.0":1240,"3.3.1":1061,"3.4.1":1012,"3.6.1":967,"1.9.1":838,"3.6.3":819,"1.8.3":749,"1.12.1":740,"1.4.4":732,"1.11.1":630,"1.10.2":565},"cdn_distribution":{"self-hosted":64535,"jquery_cdn":1268,"googleapis":1022,"cdnjs":271,"microsoft":29,"jsdelivr":13,"github_pages":9,"cloudflare":3,"unpkg":2},"page":1,"per_page":50,"total_pages":1344
... [truncated]/api/v1/jsfingerprint/library/{library}/version/{version}Search By Library Version
Find exact library+version combinations. Use Case: CVE tracking - find all scans using vulnerable version Performance: < 500ms
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
library | string | Required | Library name |
version | string | Required | Library version |
include_deprecated | boolean | Optional | Include old scans |
group_by_url | boolean | Optional | Group by unique URL |
limit | integer | Optional | Max results |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/library/jquery/version/3.6.0"Response
{"library":"jquery","version":"3.6.0","total_matches":3091,"returned_count":100,"fingerprints":[{"fingerprint_id":5036407,"scan_id":"4f87042a-bd95-4eda-bd64-d9813cbfcc3a","script_url":"https://d1v124mdoasvln.cloudfront.net/new_js/jquery-3.6.0.min.js","code_length":89501,"function_count":607,"library_detected":"jquery","library_version":"3.6.0","is_bundled":null,"bundler_type":null,"is_cdn":false,"cdn_type":null,"obfuscation_score":null,"created_at":"2026-05-05T09:44:51.752345Z"},{"fingerprint_id":5032786,"scan_id":"63157227-0ed8-458b-8a8b-aadf087ff95a","script_url":"https://www.zohowebstatic.c
... [truncated]/api/v1/jsfingerprint/bundler/{bundler_type}Search By Bundler
Find scripts by bundler type. Use Case: Build tool analysis, supply chain security Performance: < 1s
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
bundler_type | string | Required | Bundler type (webpack, rollup, vite, parcel, esbuild) |
bundle_format | string | Optional | Bundle format (esm, cjs, umd, iife, amd) |
min_confidence | number | Optional | Minimum bundler detection confidence |
include_libraries | boolean | Optional | Include detected libraries |
page | integer | Optional | Page number |
per_page | integer | Optional | Results per page |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprint/bundler/webpack?limit=3"Response
{"bundler_type":"webpack","bundle_format_filter":null,"total_bundles":10893,"unique_scans":2990,"format_breakdown":{"unknown":9587,"cjs":666,"amd":345,"iife":260,"umd":31,"esm":4},"average_bundle_size":182344,"page":1,"per_page":50,"total_pages":218,"bundles":[{"fingerprint_id":5009791,"scan_id":"981db643-8769-468f-a13c-852e95d3afb3","script_url":"https://www.inspectionsupport.com/wp-content/plugins/elementor/assets/js/webpack.runtime.min.js?ver=4.0.4","bundler_type":"webpack","bundle_format":null,"bundle_confidence":0.95,"code_length":5722,"created_at":"2026-05-04T07:49:01.558728Z","library_d
... [truncated]/api/v1/jsfingerprints/search/md5/{hash_value}Search By Md5
Search JavaScript fingerprints by MD5 hash. Only searches public scans.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_value | string | Required | |
limit | integer | Optional | Results per page |
offset | integer | Optional | Results offset |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/search/md5/ca4877aaea6ea720336eaefcd4234c20?limit=3"Response
{
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://husd.org",
"scanned_at": "2026-05-05T10:59:52.195772Z",
"script_url": "https://www.husd.org/uploaded/themes/default_24/main.js?1763056584",
"library_name": null,
"library_version": null,
"bundler_type": null,
"content_sha256": "3f08ccfa3fe55172d853efc9d5673dffa359873e6199f8175d9ca853b3924857",
"content_md5": "ca4877aaea6ea720336eaefcd4234c20",
"content_sha1": "1c98781e6979d27fff01627d11123c95c7fb611b",
"filename": "main.js"
}
],
"total": 1,
"page": 1,
"limit": 3,
"search_type": "md5",
"search_value": "ca4877aaea6ea720336eaefcd4234c20",
"context": {
"prevalence": "unique",
"prevalence_count": 1,
"prevalence_description": "Found in 1 scan. MD5 hash for cross-reference with threat intelligence databases. This is a unique script.",
"common_filenames": [
{
"filename": "main.js",
"count": 1,
"percentage": 100.0
}
],
"hash_types": {
"md5": "ca4877aaea6ea720336eaefcd4234c20",
"sha256": "3f08ccfa3fe55172d853efc9d5673dffa359873e6199f8175d9ca853b3924857",
"sha1": "1c98781e6979d27fff01627d11123c95c7fb611b"
}
}
}/api/v1/jsfingerprints/search/sha1/{hash_value}Search By Sha1
Search JavaScript fingerprints by SHA-1 hash. Only searches public scans.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hash_value | string | Required | |
limit | integer | Optional | Results per page |
offset | integer | Optional | Results offset |
Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/search/sha1/1c98781e6979d27fff01627d11123c95c7fb611b?limit=3"Response
{
"results": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"url": "https://husd.org",
"scanned_at": "2026-05-05T10:59:52.195772Z",
"script_url": "https://www.husd.org/uploaded/themes/default_24/main.js?1763056584",
"library_name": null,
"library_version": null,
"bundler_type": null,
"content_sha256": "3f08ccfa3fe55172d853efc9d5673dffa359873e6199f8175d9ca853b3924857",
"content_md5": "ca4877aaea6ea720336eaefcd4234c20",
"content_sha1": "1c98781e6979d27fff01627d11123c95c7fb611b",
"filename": "main.js"
}
],
"total": 1,
"page": 1,
"limit": 3,
"search_type": "sha1",
"search_value": "1c98781e6979d27fff01627d11123c95c7fb611b",
"context": {
"prevalence": "unique",
"prevalence_count": 1,
"prevalence_description": "Found in 1 scan. SHA-1 hash for cross-reference with legacy systems. This is a unique script.",
"common_filenames": [
{
"filename": "main.js",
"count": 1,
"percentage": 100.0
}
],
"hash_types": {
"sha1": "1c98781e6979d27fff01627d11123c95c7fb611b",
"sha256": "3f08ccfa3fe55172d853efc9d5673dffa359873e6199f8175d9ca853b3924857",
"md5": "ca4877aaea6ea720336eaefcd4234c20"
}
}
}/api/v1/jsfingerprints/{fingerprint_id}/sourceGet script source code
Retrieve the original JavaScript source code for a fingerprint from object storage
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
fingerprint_id | integer | Required | Fingerprint ID |
Response
{
"fingerprint_id": "integer",
"content_sha256": "string",
"script_url": "string",
"code_length": "integer",
"source": "string",
"retrieved_from": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/jsfingerprints/5037368/source"Response
{"fingerprint_id":5037368,"content_sha256":"3f08ccfa3fe55172d853efc9d5673dffa359873e6199f8175d9ca853b3924857","script_url":"https://www.husd.org/uploaded/themes/default_24/main.js?1763056584","code_length":33725,"source":"/*! For license information please see main.js.LICENSE.txt */\nbuildinfo={buildname:\"fs-webpack-build\",ver:\"7.1.2\",template:\"newclientcustom\",FED:\"Savu Sebastian\",PM:\"Caitlin Hazelwood\",Designer:\"Kyle Taylor\"},function(){var e={420:function(){},470:function(e,t,n){\"use strict\";n.r(t);var a=n(586);!function(){if(void 0!==window.buildinfo){var e=document.getElemen
... [truncated]/api/v1/huntsList Threat Hunts
Every hunt on the roster with its anchor, family, severity and current sighting count. A hunt is a saved detection anchored on a script fingerprint, a page-level YARA rule or an SMQL query, and it keeps matching new scans as they arrive.
Response
{
"count": "integer",
"kits": [
{
"id": "string",
"hunt_name": "string",
"hunt_family": "string",
"category": "string",
"severity": "string",
"description": "string",
"content_sha256_prefix": "string | null",
"canonical_ast_hash_prefix": "string | null",
"anchor_jsfp3_id": "integer | null",
"added_at": "string",
"reference_urls": [
"string"
],
"sightings": "integer",
"hosts": "integer",
"last_seen": "string | null"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/hunts"Response
{
"count": 170,
"kits": [
{
"id": "123e4567-e89b-12d3-a456-426614174000",
"hunt_name": "Microsoft-auth subdomain labels on non-Microsoft apexes (AiTM infrastructure tripwire)",
"hunt_family": "ms-auth-subdomain-label",
"category": "phishing",
"severity": "high",
"description": "Forward-looking tripwire for the naming convention the Payroll Pirates AiTM proxies used, rather than for the burned domains themselves. Arctic Wolf observed the proxy tier consistently fronted by ...",
"content_sha256_prefix": null,
"canonical_ast_hash_prefix": null,
"anchor_jsfp3_id": null,
"added_at": "2026-08-10 20:57:43.356699+00:00",
"reference_urls": [
"https://arcticwolf.com/resources/blog/payroll-pirates-strange-new-tides-in-business-email-compromise/"
],
"sightings": 2,
"hosts": 0,
"last_seen": "2026-09-01"
},
{
"id": "123e4567-e89b-12d3-a456-426614174000",
"hunt_name": "AiTM reverse proxy — Microsoft endpoints rewritten into the attacker's path",
"hunt_family": "aitm-proxy-url-rewrite",
"category": "phishing",
"severity": "critical",
"description": "Toolkit-agnostic detection for the structural artefact every Evilginx-style AiTM proxy leaves behind. A real AiTM relay does not clone the Microsoft sign-in page — it forwards the genuine flow and ...",
"content_sha256_prefix": null,
"canonical_ast_hash_prefix": null,
"anchor_jsfp3_id": null,
"added_at": "2026-08-10 20:57:43.356699+00:00",
"reference_urls": [
"https://arcticwolf.com/resources/blog/payroll-pirates-strange-new-tides-in-business-email-compromise/"
],
"sightings": 0,
"hosts": 0,
"last_seen": null
}
]
}/api/v1/hunts/{hunt_id}Hunt Detail and Sightings
One hunt with the scans it has matched. `hunt_id` is the public UUID; a legacy integer id is also accepted. Use `limit` to page the sightings.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hunt_id | string | Required | hunt public_id (UUID); legacy int id also accepted |
limit | integer | Optional |
Response
{
"hunt_id": "string",
"found": "boolean",
"kit": {
"hunt_name": "string",
"hunt_family": "string",
"category": "string",
"severity": "string",
"description": "string",
"reference_urls": [
"string"
],
"content_sha256": "null",
"canonical_ast_hash": "null",
"tlsh": "null",
"anchor_jsfp3_id": "null",
"added_at": "string",
"notes": "string",
"yara_rule_name": "null",
"smql_query": "string",
"id": "string"
},
"sightings_count": "integer",
"sightings": [
{
"id": "integer",
"jsfp3_id": "null",
"scan_id": "string",
"script_url": "string",
"host": "string",
"match_tier": "string",
"matched_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/hunts/e2ce78a0-ecdc-409f-b0bb-281dfd9012e1?limit=200"Response
{
"hunt_id": "123e4567-e89b-12d3-a456-426614174000",
"found": true,
"kit": {
"hunt_name": "Microsoft-auth subdomain labels on non-Microsoft apexes (AiTM infrastructure tripwire)",
"hunt_family": "ms-auth-subdomain-label",
"category": "phishing",
"severity": "high",
"description": "Forward-looking tripwire for the naming convention the Payroll Pirates AiTM proxies used, rather than for the burned domains themselves. Arctic Wolf observed the proxy tier consistently fronted by ...",
"reference_urls": [
"https://arcticwolf.com/resources/blog/payroll-pirates-strange-new-tides-in-business-email-compromise/"
],
"content_sha256": null,
"canonical_ast_hash": null,
"tlsh": null,
"anchor_jsfp3_id": null,
"added_at": "2026-08-10 20:57:43.356699+00:00",
"notes": "Measured before landing, against all 531,005 public scans on 2026-08-10: this anchor matches exactly ONE scan, msauth.o365s.com (2026-07-29) — and o365s.com is itself a Microsoft-lookalike apex who...",
"yara_rule_name": null,
"smql_query": "(domain:mslogin.* OR domain:msonline.* OR domain:msauth.* OR domain:login-microsoftonline.* OR domain:microsoftonline-*) AND -domain:*msauth.net AND -domain:*.microsoft.com AND -domain:*.microsofto...",
"id": "123e4567-e89b-12d3-a456-426614174000"
},
"sightings_count": 2,
"sightings": [
{
"id": 35799759,
"jsfp3_id": null,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "",
"host": "login-microsoftonline.cz",
"match_tier": "smql",
"matched_at": "2026-09-01 01:47:33.565996+00:00"
},
{
"id": 12436840,
"jsfp3_id": null,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "",
"host": "msauth.o365s.com",
"match_tier": "smql",
"matched_at": "2026-08-10 20:58:09.203763+00:00"
}
]
}/api/v1/huntsCreate a Threat Hunt
Register a new hunt. Requires a Bearer token with the roster role. At least one anchor is required — `content_sha256`, `canonical_ast_hash`, `tlsh`, `yara_rule_name` or `smql_query` — and existing scans matching that anchor are backfilled as sightings on creation.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hunt_name | string | Required | |
category | string | Required | |
severity | string | Optional | |
hunt_family | string | Optional | |
description | string | Optional | |
reference_urls | string | Optional | |
content_sha256 | string | Optional | |
canonical_ast_hash | string | Optional | |
tlsh | string | Optional | |
yara_rule_name | string | Optional | |
smql_query | string | Optional | |
from_jsfp3_id | string | Optional | |
notes | string | Optional |
Response
{
"created": "boolean",
"hunt_id": "string - public UUID of the new hunt",
"anchor_type": "string - which anchor the hunt was registered on",
"sightings_backfilled": "integer - existing scans matched at creation"
}Example
Request
curl -X POST "https://scanmalware.com/api/v1/hunts" \\
-H "Authorization: Bearer $TOKEN" \\
-H "Content-Type: application/json" \\
-d '{
"hunt_name": "Example credential-harvest kit",
"hunt_family": "example-kit",
"category": "phishing",
"severity": "high",
"canonical_ast_hash": "5a83c4b4e57973ba676665163ae4ec52dc793e62dab7d7f959e7af82468d91fc",
"description": "Structural fingerprint of the kit login script"
}'Response
{
"created": true,
"hunt_id": "123e4567-e89b-12d3-a456-426614174000",
"anchor_type": "canonical_ast_hash",
"sightings_backfilled": 12
}/api/v1/brandsList Impersonated Brands
Brands tracked for impersonation, with the sector each belongs to and how often it has been seen impersonated.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
limit | integer | Optional | brands per page |
offset | integer | Optional | |
sector | string | Optional | filter to one sector |
q | string | Optional | match brand name, slug or official domain |
has_sightings | boolean | Optional | true = only brands with at least one published sighting |
sort | string | Optional | sightings | hosts | recent | name |
Response
{
"count": "integer",
"brands": [
{
"id": "string",
"slug": "string",
"display_name": "string",
"sector": "string",
"logo_path": "string",
"homepage_url": "string",
"official_domains": [
"string"
],
"sightings": "integer",
"hosts": "integer",
"last_seen": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/brands"Response
{
"count": 649,
"brands": [
{
"id": "123e4567-e89b-12d3-a456-426614174000",
"slug": "instagram",
"display_name": "Instagram",
"sector": "social",
"logo_path": "/brands/instagram.png",
"homepage_url": "https://instagram.com",
"official_domains": [
"instagram.com",
"cdninstagram.com"
],
"sightings": 4680,
"hosts": 627,
"last_seen": "2026-09-02"
},
{
"id": "123e4567-e89b-12d3-a456-426614174000",
"slug": "facebook",
"display_name": "Facebook",
"sector": "social",
"logo_path": "/brands/facebook.png",
"homepage_url": "https://facebook.com",
"official_domains": [
"facebook.com",
"fb.com"
],
"sightings": 569,
"hosts": 378,
"last_seen": "2026-09-02"
}
]
}/api/v1/brands/sectorsList Brand Sectors
The sectors brands are grouped under, for filtering the brand list.
Response
{
"sectors": [
{
"sector": "string",
"brands": "integer"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/brands/sectors"Response
{
"sectors": [
{
"sector": "banking",
"brands": 88
},
{
"sector": "crypto",
"brands": 40
}
]
}/api/v1/brands/{slug_or_id}Brand Detail
One brand and the hosts caught impersonating it. Accepts either the brand slug (`instagram`) or its numeric id. Each `sightings` entry is one HOST — repeat scans of the same host are grouped into its `sightings` count, with `verdict`/`title` taken from the newest scan — so `limit` bounds hosts, not raw sightings.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
slug_or_id | string | Required | brand slug (e.g. 'microsoft'), public_id UUID, or legacy int id |
limit | integer | Optional | |
cursor | string | Optional | opaque cursor from `next_cursor` |
Response
{
"brand_id": "string",
"found": "boolean",
"brand": {
"slug": "string",
"display_name": "string",
"aliases": [
"string"
],
"official_domains": [
"string"
],
"sector": "string",
"homepage_url": "string",
"logo_path": "string",
"trusted_auth_hosts": [],
"is_impersonation_target": "boolean",
"description": "null",
"reference_urls": [],
"added_at": "string",
"id": "string"
},
"total_sightings": "integer",
"total_hosts": "integer",
"last_seen": "string",
"hosts_shown": "integer",
"sightings_count": "integer",
"sightings": [
{
"scan_id": "string",
"host": "string",
"sightings": "integer",
"match_tiers": [
"string"
],
"detected_by": [
"string"
],
"confidence": "string",
"first_seen": "string",
"last_seen": "string",
"title": "string",
"verdict": "string",
"risk_level": "string",
"overall_score": "number"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/brands/instagram?limit=100"Response
{
"brand_id": "123e4567-e89b-12d3-a456-426614174000",
"found": true,
"brand": {
"slug": "instagram",
"display_name": "Instagram",
"aliases": [],
"official_domains": [
"instagram.com",
"cdninstagram.com"
],
"sector": "social",
"homepage_url": "https://instagram.com",
"logo_path": "/brands/instagram.png",
"trusted_auth_hosts": [],
"is_impersonation_target": true,
"description": null,
"reference_urls": [],
"added_at": "2026-07-01T12:27:08.117578+00:00",
"id": "123e4567-e89b-12d3-a456-426614174000"
},
"total_sightings": 4695,
"total_hosts": 631,
"last_seen": "2026-09-03",
"hosts_shown": 100,
"sightings_count": 100,
"sightings": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"host": "www.facebook.com",
"sightings": 3936,
"match_tiers": [
"title"
],
"detected_by": [
"security-analyzer"
],
"confidence": "medium",
"first_seen": "2026-07-02T09:11:03.441201+00:00",
"last_seen": "2026-09-03T06:44:12.092727+00:00",
"title": "Meta for Business | Page Appeal",
"verdict": "Malicious (Instagram Phishing, cloaked from scanners)",
"risk_level": "malicious",
"overall_score": 90
},
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"host": "facebook-trial.vercel.app",
"sightings": 1,
"match_tiers": [
"title"
],
"detected_by": [
"security-analyzer"
],
"confidence": "medium",
"first_seen": "2026-09-03T05:02:41.118330+00:00",
"last_seen": "2026-09-03T05:02:41.118330+00:00",
"title": "facebook",
"verdict": "High Risk (Credential Phishing on disposable hosting)",
"risk_level": "high",
"overall_score": 60
}
]
}/api/v1/js-fingerprinting3/scan/{scan_id}Structural Fingerprints for a Scan
Every script fingerprinted on a scan: content and canonical-AST hashes, parse status, matched library, and any hunt the script anchors.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan UUID |
Response
{
"scan_id": "string",
"count": "integer",
"fingerprints": [
{
"id": "integer",
"script_url": "string",
"module_of": "integer | null",
"ok": "boolean",
"content_sha256": "string",
"normalized_source_hash": "string",
"canonical_ast_hash": "string",
"tlsh": "string",
"node_count": "integer",
"fp_version": "string",
"error": "null",
"lib_match_name": "null",
"lib_match_version": "null",
"lib_match_url": "null",
"lib_match_confidence": "null",
"hunt_id": "null",
"hunt_name": "null",
"hunt_family": "null",
"hunt_category": "null",
"hunt_severity": "null",
"hunt_description": "null",
"hunt_match_tier": "null",
"content_seen": "integer",
"canonical_seen": "integer"
}
],
"page_hunts": []
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinting3/scan/cd8bf479-8fed-4ce1-9f38-6f5913d0ded2"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"count": 356,
"fingerprints": [
{
"id": 35936148,
"script_url": "https://client.crisp.chat/l.js",
"module_of": null,
"ok": true,
"content_sha256": "5346c0fba95b59fe91d5b499d72760b7be1f30d0b8ca053a33127c70e7652d85",
"normalized_source_hash": "80027d7fa6035d79d6c80df044a852cd8a6842c3911f2ad054c1a8505a91f999",
"canonical_ast_hash": "cd42999ebe87d92100310a8f17e2f9b68ea5edb57605c41269df3b19745d6139",
"tlsh": "T187F1731732696132059362AA163B2B49F43361295CC5C15CB169ECF12D7CA8FA13BFFE",
"node_count": 2133,
"fp_version": "jsfp3-p2-0.1",
"error": null,
"lib_match_name": null,
"lib_match_version": null,
"lib_match_url": null,
"lib_match_confidence": null,
"hunt_id": null,
"hunt_name": null,
"hunt_family": null,
"hunt_category": null,
"hunt_severity": null,
"hunt_description": null,
"hunt_match_tier": null,
"content_seen": 12,
"canonical_seen": 64
},
{
"id": 35936149,
"script_url": "https://client.crisp.chat/static/javascripts/client_default_72e015d.js",
"module_of": null,
"ok": true,
"content_sha256": "1052d0aebb499d920a1026295bc9c33e0e69c62e0a6b7c333b20db0fc5ff4df9",
"normalized_source_hash": "94d27b8f44f3b7ee9e474a29d89fcc3eaca6ba3a07d070b26ae7732026dc7a38",
"canonical_ast_hash": "2318a498e31a58caa465086e9baee1370b6ab405c49732fa443b477e71d76cb8",
"tlsh": "T18F442A8A3265A83313F642C3A4720582F33625AD2886407CB76CADEF6A5CDC571E7F75",
"node_count": 84469,
"fp_version": "jsfp3-p2-0.1",
"error": null,
"lib_match_name": null,
"lib_match_version": null,
"lib_match_url": null,
"lib_match_confidence": null,
"hunt_id": null,
"hunt_name": null,
"hunt_family": null,
"hunt_category": null,
"hunt_severity": null,
"hunt_description": null,
"hunt_match_tier": null,
"content_seen": 13,
"canonical_seen": 13
}
],
"page_hunts": []
}/api/v1/js-fingerprinting3/canonical/{canonical_ast_hash}Search by Canonical AST Hash
Find every script sharing a canonical AST hash — the structural fingerprint, which survives renaming and reformatting, so it matches a kit across obfuscation changes.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
canonical_ast_hash | string | Required | canonical_ast_hash |
limit | integer | Optional |
Response
{
"canonical_ast_hash": "string",
"matches_found": "integer",
"matches": [
{
"scan_id": "string",
"script_url": "string",
"content_sha256": "string",
"node_count": "integer",
"created_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinting3/canonical/5a83c4b4e57973ba676665163ae4ec52dc793e62dab7d7f959e7af82468d91fc?limit=100"Response
{
"canonical_ast_hash": "5a83c4b4e57973ba676665163ae4ec52dc793e62dab7d7f959e7af82468d91fc",
"matches_found": 18,
"matches": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://krejubhnota64.pages.dev/js/landers/survey-pick-a-box/app.js?id=17138759790b445ece6b",
"content_sha256": "8c5d5c1280347ed451ee71f700726247525c3c183de830af2f1fb0b4b9a661f0",
"node_count": 48683,
"created_at": "2026-09-02T17:58:49.510317+00:00"
},
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://glkardunteh38.pages.dev/js/landers/survey-pick-a-box/app.js?id=17138759790b445ece6b",
"content_sha256": "8c5d5c1280347ed451ee71f700726247525c3c183de830af2f1fb0b4b9a661f0",
"node_count": 48683,
"created_at": "2026-09-02T07:14:46.668462+00:00"
}
]
}/api/v1/js-fingerprinting3/content/{content_sha256}Search by Exact Script Content
Find every scan that loaded a byte-identical script, by SHA-256 of its content.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
content_sha256 | string | Required | content SHA-256 |
limit | integer | Optional |
Response
{
"content_sha256": "string",
"matches_found": "integer",
"matches": [
{
"scan_id": "string",
"script_url": "string",
"created_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinting3/content/8c5d5c1280347ed451ee71f700726247525c3c183de830af2f1fb0b4b9a661f0?limit=100"Response
{
"content_sha256": "8c5d5c1280347ed451ee71f700726247525c3c183de830af2f1fb0b4b9a661f0",
"matches_found": 15,
"matches": [
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://krejubhnota64.pages.dev/js/landers/survey-pick-a-box/app.js?id=17138759790b445ece6b",
"created_at": "2026-09-02T17:58:49.510317+00:00"
},
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://glkardunteh38.pages.dev/js/landers/survey-pick-a-box/app.js?id=17138759790b445ece6b",
"created_at": "2026-09-02T07:14:46.668462+00:00"
}
]
}/api/v1/js-fingerprinting3/similar/{row_id}Structurally Similar Scripts
Scripts structurally close to a given fingerprint row, ranked by distance. Takes the numeric `id` from a fingerprint record, not a hash.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
row_id | integer | Required | js_fingerprinting3.id of the anchor |
limit | integer | Optional | |
min_similarity | number | Optional |
Response
{
"row_id": "integer",
"matches_found": "integer",
"min_similarity": "number",
"matches": [
{
"id": "integer",
"scan_id": "string",
"script_url": "string",
"canonical_ast_hash": "string",
"similarity": "number",
"node_count": "integer",
"is_module": "boolean",
"fingerprint_id": "integer | null",
"code_length": "integer | null",
"scan_created_at": "string",
"library_detected": "string | null",
"library_version": "string | null",
"final_url": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinting3/similar/35935676?limit=50"Response
{
"row_id": 35935676,
"matches_found": 20,
"min_similarity": 0.9,
"matches": [
{
"id": 611264,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://comune.casatenovo.lc.it/js/vendor.js?id=51393c43603619bb4dc3428991cdd7b4",
"canonical_ast_hash": "3c5141c0583b250a9924faa9547ef40f340472cbf80f38060d809ab05855dc30",
"similarity": 0.9693658642528398,
"node_count": 96647,
"is_module": false,
"fingerprint_id": null,
"code_length": null,
"scan_created_at": "2026-05-23T01:57:38.203903+00:00",
"library_detected": null,
"library_version": null,
"final_url": "https://comune.casatenovo.lc.it/"
},
{
"id": 3791383,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "https://comune.guardiagrele.ch.it/js/vendor.js?id=51393c43603619bb4dc3428991cdd7b4",
"canonical_ast_hash": "3c5141c0583b250a9924faa9547ef40f340472cbf80f38060d809ab05855dc30",
"similarity": 0.9693658642528398,
"node_count": 96647,
"is_module": false,
"fingerprint_id": 2959785,
"code_length": 267618,
"scan_created_at": "2026-01-23T23:18:14.079824+00:00",
"library_detected": "vendor-bundle",
"library_version": null,
"final_url": "https://comune.guardiagrele.ch.it/"
}
]
}/api/v1/js-fingerprinting3/statsStructural Fingerprint Coverage
Corpus-wide coverage counters: fingerprint rows, scans covered, rows that parsed, and how many distinct structural and content hashes exist.
Response
{
"rows": "integer",
"scans": "integer",
"parsed_ok": "integer",
"distinct_canonical": "integer",
"distinct_content": "integer"
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinting3/stats"Response
{
"rows": 33730005,
"scans": 241503,
"parsed_ok": 33521335,
"distinct_canonical": 2756332,
"distinct_content": 5858543
}/api/v1/js-fingerprinting3/huntsList Hunts (legacy alias)
Backward-compatible alias of GET /api/v1/hunts. The roster is no longer JS-specific; prefer /api/v1/hunts in new code.
Response
{
"count": "integer",
"kits": [
{
"id": "string",
"hunt_name": "string",
"hunt_family": "string",
"category": "string",
"severity": "string",
"description": "string",
"content_sha256_prefix": "string | null",
"canonical_ast_hash_prefix": "string | null",
"anchor_jsfp3_id": "integer | null",
"added_at": "string",
"reference_urls": [
"string"
],
"sightings": "integer",
"hosts": "integer",
"last_seen": "string | null"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinting3/hunts"Response
{
"count": 170,
"kits": [
{
"id": "123e4567-e89b-12d3-a456-426614174000",
"hunt_name": "Microsoft-auth subdomain labels on non-Microsoft apexes (AiTM infrastructure tripwire)",
"hunt_family": "ms-auth-subdomain-label",
"category": "phishing",
"severity": "high",
"description": "Forward-looking tripwire for the naming convention the Payroll Pirates AiTM proxies used, rather than for the burned domains themselves. Arctic Wolf observed the proxy tier consistently fronted by ...",
"content_sha256_prefix": null,
"canonical_ast_hash_prefix": null,
"anchor_jsfp3_id": null,
"added_at": "2026-08-10T20:57:43.356699+00:00",
"reference_urls": [
"https://arcticwolf.com/resources/blog/payroll-pirates-strange-new-tides-in-business-email-compromise/"
],
"sightings": 2,
"hosts": 0,
"last_seen": "2026-09-01"
},
{
"id": "123e4567-e89b-12d3-a456-426614174000",
"hunt_name": "AiTM reverse proxy — Microsoft endpoints rewritten into the attacker's path",
"hunt_family": "aitm-proxy-url-rewrite",
"category": "phishing",
"severity": "critical",
"description": "Toolkit-agnostic detection for the structural artefact every Evilginx-style AiTM proxy leaves behind. A real AiTM relay does not clone the Microsoft sign-in page — it forwards the genuine flow and ...",
"content_sha256_prefix": null,
"canonical_ast_hash_prefix": null,
"anchor_jsfp3_id": null,
"added_at": "2026-08-10T20:57:43.356699+00:00",
"reference_urls": [
"https://arcticwolf.com/resources/blog/payroll-pirates-strange-new-tides-in-business-email-compromise/"
],
"sightings": 0,
"hosts": 0,
"last_seen": null
}
]
}/api/v1/js-fingerprinting3/huntsCreate a Hunt (legacy alias)
Backward-compatible alias of POST /api/v1/hunts. Prefer /api/v1/hunts in new code.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hunt_name | string | Required | |
category | string | Required | |
severity | string | Optional | |
hunt_family | string | Optional | |
description | string | Optional | |
reference_urls | string | Optional | |
content_sha256 | string | Optional | |
canonical_ast_hash | string | Optional | |
tlsh | string | Optional | |
yara_rule_name | string | Optional | |
smql_query | string | Optional | |
from_jsfp3_id | string | Optional | |
notes | string | Optional |
Response
{
"created": "boolean",
"hunt_id": "string - public UUID of the new hunt",
"anchor_type": "string - which anchor the hunt was registered on",
"sightings_backfilled": "integer - existing scans matched at creation"
}Example
Request
curl -X POST "https://scanmalware.com/api/v1/js-fingerprinting3/hunts" \\
-H "Authorization: Bearer $TOKEN" \\
-H "Content-Type: application/json" \\
-d '{
"hunt_name": "Example credential-harvest kit",
"category": "phishing",
"canonical_ast_hash": "5a83c4b4e57973ba676665163ae4ec52dc793e62dab7d7f959e7af82468d91fc"
}'Response
{
"created": true,
"hunt_id": "123e4567-e89b-12d3-a456-426614174000",
"anchor_type": "canonical_ast_hash",
"sightings_backfilled": 12
}/api/v1/js-fingerprinting3/hunt/{hunt_id}Hunt Detail (legacy alias)
Backward-compatible alias of GET /api/v1/hunts/{hunt_id}. Prefer /api/v1/hunts in new code.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
hunt_id | string | Required | hunt public_id (UUID); legacy int id also accepted |
limit | integer | Optional |
Response
{
"hunt_id": "string",
"found": "boolean",
"kit": {
"hunt_name": "string",
"hunt_family": "string",
"category": "string",
"severity": "string",
"description": "string",
"reference_urls": [
"string"
],
"content_sha256": "null",
"canonical_ast_hash": "null",
"tlsh": "null",
"anchor_jsfp3_id": "null",
"added_at": "string",
"notes": "string",
"yara_rule_name": "null",
"smql_query": "string",
"id": "string"
},
"sightings_count": "integer",
"sightings": [
{
"id": "integer",
"jsfp3_id": "null",
"scan_id": "string",
"script_url": "string",
"host": "string",
"match_tier": "string",
"matched_at": "string"
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/js-fingerprinting3/hunt/e2ce78a0-ecdc-409f-b0bb-281dfd9012e1?limit=200"Response
{
"hunt_id": "123e4567-e89b-12d3-a456-426614174000",
"found": true,
"kit": {
"hunt_name": "Microsoft-auth subdomain labels on non-Microsoft apexes (AiTM infrastructure tripwire)",
"hunt_family": "ms-auth-subdomain-label",
"category": "phishing",
"severity": "high",
"description": "Forward-looking tripwire for the naming convention the Payroll Pirates AiTM proxies used, rather than for the burned domains themselves. Arctic Wolf observed the proxy tier consistently fronted by ...",
"reference_urls": [
"https://arcticwolf.com/resources/blog/payroll-pirates-strange-new-tides-in-business-email-compromise/"
],
"content_sha256": null,
"canonical_ast_hash": null,
"tlsh": null,
"anchor_jsfp3_id": null,
"added_at": "2026-08-10T20:57:43.356699+00:00",
"notes": "Measured before landing, against all 531,005 public scans on 2026-08-10: this anchor matches exactly ONE scan, msauth.o365s.com (2026-07-29) — and o365s.com is itself a Microsoft-lookalike apex who...",
"yara_rule_name": null,
"smql_query": "(domain:mslogin.* OR domain:msonline.* OR domain:msauth.* OR domain:login-microsoftonline.* OR domain:microsoftonline-*) AND -domain:*msauth.net AND -domain:*.microsoft.com AND -domain:*.microsofto...",
"id": "123e4567-e89b-12d3-a456-426614174000"
},
"sightings_count": 2,
"sightings": [
{
"id": 35799759,
"jsfp3_id": null,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "",
"host": "login-microsoftonline.cz",
"match_tier": "smql",
"matched_at": "2026-09-01T01:47:33.565996+00:00"
},
{
"id": 12436840,
"jsfp3_id": null,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "",
"host": "msauth.o365s.com",
"match_tier": "smql",
"matched_at": "2026-08-10T20:58:09.203763+00:00"
}
]
}/api/v1/segments/by-scan/{scan_id}/securitySecurity-Relevant Script Segments
Segments of a scan’s JavaScript that matched a malware pattern or carry a security-relevant finding.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
scan_id | string | Required | Scan ID (uuid) whose segments to assess |
limit | integer | Optional |
Response
{
"scan_id": "string",
"total_segments": "integer",
"segments": [
{
"segment_id": "integer",
"scan_id": "string",
"script_url": "string",
"function_name": "string | null",
"code_length": "integer",
"security": {
"risk_score": "integer",
"severity": "string",
"total_matches": "integer",
"average_confidence": "integer",
"threat_categories": [],
"pattern_matches": [],
"static_risk_score": "integer",
"risk_factors": [
"string"
],
"library_match": "null"
}
}
]
}Example
Request
curl "https://scanmalware.com/api/v1/segments/by-scan/cd8bf479-8fed-4ce1-9f38-6f5913d0ded2/security?limit=50"Response
{
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"total_segments": 200,
"segments": [
{
"segment_id": 5638098574,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "(inline)",
"function_name": null,
"code_length": 102,
"security": {
"risk_score": 0,
"severity": "NONE",
"total_matches": 0,
"average_confidence": 0,
"threat_categories": [],
"pattern_matches": [],
"static_risk_score": 0,
"risk_factors": [],
"library_match": "jquery"
}
},
{
"segment_id": 5638098575,
"scan_id": "123e4567-e89b-12d3-a456-426614174000",
"script_url": "(inline)",
"function_name": null,
"code_length": 283,
"security": {
"risk_score": 0,
"severity": "NONE",
"total_matches": 0,
"average_confidence": 0,
"threat_categories": [],
"pattern_matches": [],
"static_risk_score": 0,
"risk_factors": [],
"library_match": "jquery"
}
}
]
}/api/v1/stats/load-time-distributionScan Load-Time Distribution
How scanned pages are distributed across load-time buckets.
Response
{
"available": "boolean",
"sample_size": "integer",
"median_seconds": "number",
"band_edges_seconds": {
"very_fast_max": "number",
"fast_max": "number",
"medium_max": "number"
},
"percentiles_seconds": {
"1": "number",
"5": "number",
"10": "number",
"15": "number",
"20": "number",
"25": "number",
"30": "number",
"35": "number",
"40": "number",
"45": "number",
"50": "number",
"55": "number",
"60": "number",
"65": "number",
"70": "number",
"75": "number",
"80": "number",
"85": "number",
"90": "number",
"95": "number",
"99": "number"
},
"note": "string"
}Example
Request
curl "https://scanmalware.com/api/v1/stats/load-time-distribution"Response
{
"available": true,
"sample_size": 429305,
"median_seconds": 3.62,
"band_edges_seconds": {
"very_fast_max": 1.05,
"fast_max": 3.62,
"medium_max": 11.42
},
"percentiles_seconds": {
"1": 0.13,
"5": 0.244,
"10": 0.411,
"15": 0.575,
"20": 0.77,
"25": 1.046,
"30": 1.405,
"35": 1.84,
"40": 2.299,
"45": 2.848,
"50": 3.618,
"55": 4.656,
"60": 5.912,
"65": 7.58,
"70": 8.197,
"75": 11.422,
"80": 16.883,
"85": 27.47,
"90": 39.321,
"95": 83.487,
"99": 244.936
},
"note": "Scanner-measured page-load time across completed scans (0<t<600s); comparison is vs. other scanned sites, not real-user Web Vitals."
}/robots.txtCrawler Directives
The site’s robots.txt. Served as text/plain. /api/ is disallowed for crawlers: page content is server-rendered, so the JSON endpoints add no indexable content.
Response
string - text/plainExample
Request
curl "https://scanmalware.com/robots.txt"Response
# Robots.txt for ScanMalware.com
# Allow all crawlers including AI systems
User-agent: *
Disallow: /api/
Allow: /
Sitemap: https://scanmalware.com/sitemap.xml/sitemap.xmlSitemap
The XML sitemap. Served as application/xml, generated from indexable pages.
Response
string - application/xmlExample
Request
curl "https://scanmalware.com/sitemap.xml"Response
<?xml version="1.0" encoding="UTF-8"?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
<url>
<loc>https://scanmalware.com/</loc>
<lastmod>2026-09-02</lastmod>
<changefreq>daily</changefreq>
<priority>1.0</priority>
</url>
</urlset>/sitemap.xml.gzSitemap (gzipped)
The same sitemap, gzip-compressed. Served as application/xml; the body is gzip data, so decompress before parsing.
Response
binary - gzip-compressed application/xmlExample
Request
curl "https://scanmalware.com/sitemap.xml.gz" | gunzipResponse
<gzip-compressed XML; ~340 KB, decompress with gunzip>/api/v1/brands/{slug_or_id}/exportBrand Export
The published host rows as CSV or JSON, for offline analysis.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
slug_or_id | string | Required | |
format | string | Optional | |
limit | integer | Optional |
Example
Request
curl "https://scanmalware.com/api/v1/brands/{slug_or_id}/export"Response
/api/v1/brands/{slug_or_id}/timelineBrand Timeline
Published sightings and distinct hosts per day, oldest first. Exists so this can be consumed as a feed rather than read as a web page — a brand-protection team wants the delta, not the gallery.
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
slug_or_id | string | Required | |
days | integer | Optional |
Example
Request
curl "https://scanmalware.com/api/v1/brands/{slug_or_id}/timeline"Response
/api/v1/health/depsHealth Dependencies
Dependency health for MONITORING. Deliberately NOT the Swarm probe. Returns 503 when Redis or the database is unreachable, so a caller can act on the status code instead of parsing a body. ⚠️ WHY THIS IS A SEPARATE ENDPOINT FROM `/api/v1/health`, and why nothing should quietly wire Swarm to it: `/api/v1/health` is the container probe (`swarm/stack.yml`, `urlopen(...)` every 30s, 3 retries). It is a LIVENESS check -- is the process serving HTTP -- and that is the right shape for a restart trigger. Pointing an orchestrator at a DEPENDENCY check means a Redis blip or a saturated pool restarts the API, which is most likely to happen during exactly the incident you least want it cycling in. Changing that is a decision with a blast radius; measure how often these checks would trip before anyone makes it. History (2026-09-08): `/api/v1/health` was declared TWICE. The first registration -- a static `return {"status": "ok", ...}` -- won, so the second, a 167-line handler that really did check Redis, Postgres, storage, antivirus and workers, had never served a request. The probe therefore could not fail on a dependency. The dead handler was removed rather than promoted, because it ALWAYS returned HTTP 200 too: it reported state in the body, and the probe never reads the body. Promoting it would have looked like a fix and changed nothing. Its richer signals (storage, antivirus, worker counts, queue depth) had no consumer and are in git history if ever wanted.
Example
Request
curl "https://scanmalware.com/api/v1/health/deps"Response