URL Threat Detection API

Deep AI-powered analysis for investigating suspicious URLs with multi-agent threat detection and evidence-based reporting.

Overview

What is URL Threat Detection?

URL Threat Detection is our comprehensive, AI-powered security analysis service that performs deep investigation of suspicious URLs. Unlike basic domain checks, this API scrapes page content, analyzes screenshots, and uses multi-agent AI to detect zero-day threats and sophisticated phishing attacks.

Asynchronous
20-40 seconds
Pricing
$0.02/scan
Multi-Agent AI
4 specialist agents

What It Analyzes

URL patterns and domain infrastructure
DNS, RDAP, and SSL validation
Full page content scraping (HTML, scripts)
Screenshot analysis with AI vision models
Brand impersonation detection
Evidence-based threat classification

Typical Use Cases

  • Investigating URLs reported by users or security tools
  • Detecting brand impersonation and phishing attacks
  • Security incident response and forensic analysis
  • Analyzing URLs that failed initial domain-level screening

Creating a Scan

Send a POST request to start a new URL scan. The scan will be processed asynchronously, and you'll receive a scan ID to check the status.

Endpoint

POST https://api.urlert.com/v1/scans

Request Body

{
  "url": "https://example.com"
}

Code Examples

curl -X POST https://api.urlert.com/v1/scans \
  -H "Authorization: Bearer u_sk_your_api_token_here" \
  -H "Content-Type: application/json" \
  -d '{"url": "https://example.com"}'

Response (201 Created)

{
  "scan_id": "550e8400-e29b-41d4-a716-446655440000",
  "status": "pending",
  "created_at": "2024-01-15T10:30:00Z"
}

Checking Scan Status

Use the scan ID from the create response to check the status and retrieve results once the scan is complete. Poll this endpoint until the status is completed or failed.

Polling Guidance: Most scans complete within 30-60 seconds. Poll every 3-5 seconds to check status. Avoid polling more frequently to stay within rate limits.

Endpoint

GET https://api.urlert.com/v1/scans/{scan_id}

Code Examples with Polling

import requests
import time

scan_id = '550e8400-e29b-41d4-a716-446655440000'
headers = {'Authorization': 'Bearer u_sk_your_api_token_here'}

# Poll until scan completes
while True:
    response = requests.get(
        f'https://api.urlert.com/v1/scans/{scan_id}',
        headers=headers
    )
    data = response.json()
    
    if data['status'] in ['completed', 'failed']:
        break
    
    print(f"Status: {data['status']}, waiting...")
    time.sleep(5)  # Wait 5 seconds before next check

print(f"Final status: {data['status']}")
if data['status'] == 'completed':
    print(f"Assessment: {data['report']['final_assessment']}")

Scan Statuses

pending Pending
Scan is queued and waiting to start
processing Processing
Scan is currently running
completed Completed
Scan finished successfully, results available
failed Failed
Scan encountered an error

Response Schema

Detailed structure of the scan response object. The report field is only present when status is completed.

Top-Level Fields

Field Type Description
scan_id string UUID of the scan
url string The URL that was scanned
status enum Current status: pending, processing, completed, failed
created_at string ISO 8601 timestamp when scan was created
completed_at string? ISO 8601 timestamp when scan completed (null if not completed)
report object? Final analysis report (only when status is completed)
error string? Error message (only when status is failed)

Example Responses

Rate Limiting

All API endpoints are rate limited on a per-organization, per-minute basis. Rate limits are enforced using a sliding window algorithm to ensure fair usage.

Default Rate Limits

Operation Limit Description
POST /v1/scans 10/minute Create new URL scans
GET /v1/scans/:id 60/minute Check scan status and results

Rate Limit Headers

Every API response includes headers that help you track your rate limit status:

X-RateLimit-Limit: 60
X-RateLimit-Remaining: 45
X-RateLimit-Reset: 1705315800
  • X-RateLimit-Limit Maximum requests allowed per minute
  • X-RateLimit-Remaining Requests remaining in current window
  • X-RateLimit-Reset Unix timestamp when the rate limit resets

Handling Rate Limit Errors

When you exceed your rate limit, you'll receive a 429 Too Many Requests response with a Retry-After header indicating how long to wait:

HTTP/1.1 429 Too Many Requests
X-RateLimit-Limit: 10
X-RateLimit-Remaining: 0
X-RateLimit-Reset: 1705315800
Retry-After: 42

{
  "error": "rate_limit_exceeded",
  "message": "Rate limit exceeded. Try again in 42 seconds.",
  "limit": 10,
  "retry_after": 42
}

Best Practices

  • Monitor Headers: Check rate limit headers in responses to track your usage and avoid hitting limits.
  • Implement Backoff: When you receive a 429 error, respect the Retry-After header value before retrying.
  • Batch When Possible: For read operations, consider implementing caching to reduce the number of API calls.
  • Poll Responsibly: When polling for scan results, use intervals of 3-5 seconds to stay well within the read rate limit.

Best Practices

  • Poll Every 3-5 Seconds: Most scans complete within 30-60 seconds. Polling more frequently may hit rate limits (60 requests/minute for reads).
  • Store Scan IDs: Save the scan_id from the create response to check results later or for record-keeping.
  • Handle All Statuses: Your integration should gracefully handle all scan statuses (pending, processing, completed, failed).
  • Secure Your Token: Never expose your API token in client-side code or public repositories. Use environment variables.
  • Handle Errors: Always check response status codes and handle errors appropriately (insufficient balance, rate limits, etc.).