RankDisco API Reference
Complete API endpoint documentation for RankDisco (RankFabric Edge Worker).
API Overview
Base URL
Production: https://api.rankdisco.com
Development: https://rankdisco-api.your-subdomain.workers.dev
Authentication
All API endpoints (except webhooks and public endpoints) require authentication via API key.
Header Authentication (Recommended)
Authorization: Bearer YOUR_API_KEY
Query Parameter Authentication
GET /api/endpoint?api_key=YOUR_API_KEY
Rate Limits
| Tier | Requests/minute | Burst |
|---|---|---|
| Free | 60 | 100 |
| Pro | 300 | 500 |
| Enterprise | Unlimited | Unlimited |
Response Format
All responses are JSON with consistent structure:
Success Response
{
"success": true,
"data": { ... },
"count": 100,
"pagination": {
"limit": 50,
"offset": 0,
"has_more": true
}
}
Error Response
{
"error": "Error message",
"details": "Additional context",
"status": 400
}
Common HTTP Status Codes
| Code | Description |
|---|---|
| 200 | Success |
| 201 | Created |
| 400 | Bad Request - Invalid parameters |
| 401 | Unauthorized - Invalid or missing API key |
| 404 | Not Found |
| 429 | Rate Limited |
| 500 | Internal Server Error |
Endpoint Categories
- Projects - Project management
- Assets - Asset management (websites, apps, local businesses)
- Keywords - Keyword research and tracking
- Rankings - SERP and App Store rankings
- Apps - App Store intelligence
- Domains - Domain management and metrics
- Admin - Administrative operations
- Webhooks - External callback handlers
Projects
Create Project
Creates a new project for organizing tracking subscriptions.
POST /api/projects
Request Body
{
"organization_id": "org_abc123",
"name": "My Project",
"description": "Optional description",
"settings": {
"default_location_code": 2840,
"default_language_code": "en"
}
}
Response
{
"success": true,
"project": {
"id": "proj_xyz789",
"organization_id": "org_abc123",
"name": "My Project",
"description": "Optional description",
"status": "active",
"settings": { ... },
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T10:30:00Z"
}
}
Error Codes
| Code | Description |
|---|---|
| 400 | Missing required fields (organization_id, name) |
| 500 | Database error |
List Projects
GET /api/projects?organization_id={org_id}&status={status}&limit={limit}&offset={offset}
Query Parameters
| Parameter | Type | Required | Default | Description |
|---|---|---|---|---|
| organization_id | string | Yes | - | Organization ID |
| status | string | No | active | Filter: active, paused, archived, all |
| limit | integer | No | 100 | Max results (max: 500) |
| offset | integer | No | 0 | Pagination offset |
Response
{
"success": true,
"projects": [
{
"id": "proj_xyz789",
"name": "My Project",
"status": "active",
...
}
],
"count": 10,
"total": 25,
"pagination": {
"limit": 100,
"offset": 0,
"has_more": false
}
}
Get Project
GET /api/projects/{project_id}
Response
{
"success": true,
"project": {
"id": "proj_xyz789",
"name": "My Project",
"status": "active",
"stats": {
"total_keywords": 150,
"total_apps": 5,
"total_assets": 12
},
...
}
}
Update Project
PUT /api/projects/{project_id}
Request Body
{
"name": "Updated Name",
"description": "Updated description",
"status": "paused",
"settings": { ... }
}
Delete Project
Soft-deletes a project by setting status to archived.
DELETE /api/projects/{project_id}
Assets
Assets represent your owned properties: websites, apps, and local businesses.
Create Asset
POST /api/assets
Request Body (Website)
{
"project_id": "proj_xyz789",
"type": "website",
"value": "example.com",
"name": "My Website",
"skip_onboarding": false,
"backlinks_limit": 100,
"keywords_limit": 100
}
Request Body (iOS App)
{
"project_id": "proj_xyz789",
"type": "app_ios",
"value": "123456789",
"name": "My App",
"platform": "apple",
"icon_url": "https://...",
"app_id": "123456789",
"bundle_id": "com.example.app"
}
Request Body (Local Business)
{
"project_id": "proj_xyz789",
"type": "local",
"value": "ChIJ...",
"name": "My Business",
"place_id": "ChIJ...",
"cid": "12345678901234567890",
"location_id": 1026201,
"lat": 30.2672,
"lng": -97.7431,
"address": "123 Main St, Austin, TX",
"phone": "+1-512-555-1234"
}
Response
{
"success": true,
"id": "asset_abc123",
"message": "Asset saved",
"domain_id": 456,
"onboarding": {
"started": true,
"orchestration": "workflow",
"workflow_id": "wf_xyz",
"status_url": "/api/admin/workflow/asset-onboard/wf_xyz"
}
}
List Assets
GET /api/assets?project_id={project_id}
Response
{
"assets": [
{
"id": "asset_abc123",
"project_id": "proj_xyz789",
"type": "website",
"value": "example.com",
"name": "My Website",
"platform": null,
"icon_url": null,
"meta_json": "{}",
"created_at": 1705315800000,
"updated_at": 1705315800000
}
]
}
Get Asset
GET /api/assets/{asset_id}
Update Asset
PUT /api/assets/{asset_id}
Request Body
{
"name": "Updated Name",
"icon_url": "https://...",
"meta": { "key": "value" }
}
Delete Asset
DELETE /api/assets/{asset_id}
Keywords
Track Keywords
Start tracking keywords for SERP rankings.
POST /api/keywords/track
Request Body (Single Keyword)
{
"project_id": "proj_xyz789",
"keyword_text": "best seo tools",
"location_code": 2840,
"language_code": "en",
"device": "desktop",
"target_domain": "example.com"
}
Request Body (Batch)
{
"keywords": [
{
"project_id": "proj_xyz789",
"keyword_text": "best seo tools",
"location_code": 2840,
"language_code": "en",
"device": "desktop"
},
{
"project_id": "proj_xyz789",
"keyword_text": "seo software",
"location_code": 2840,
"language_code": "en",
"device": "mobile"
}
]
}
Response
{
"success": true,
"message": "Keywords successfully added to tracking",
"keywords_tracked": 2,
"keywords": [
{
"keyword_id": "kw_abc123",
"keyword_text": "best seo tools",
"status": "tracking",
"serp_queued": true
}
],
"serp_tracking": {
"orchestration": "workflow",
"keywords_queued": 2
},
"estimated_completion": "2024-01-15T10:35:00Z"
}
Keyword Suggestions
Get related keywords with search volume data.
POST /api/keywords/suggestions
Request Body
{
"keyword": "seo tools",
"location_code": 2840,
"language_code": "en",
"limit": 100,
"include_seed_keyword": true,
"include_serp_info": false
}
Response
{
"success": true,
"count": 100,
"data": {
"seed_keyword": "seo tools",
"total_count": 5432,
"items_count": 100,
"keywords": [
{
"keyword": "free seo tools",
"keyword_info": {
"search_volume": 12100,
"competition": 0.45,
"competition_level": "MEDIUM",
"cpc": 5.23,
"categories": [10003, 10004]
},
"category_names": ["Software", "Internet & Telecom"]
}
]
}
}
Keyword Overview
Get comprehensive keyword data including 84-month history.
POST /api/keywords/overview
Request Body
{
"keywords": ["seo tools", "keyword research"],
"location_code": 2840,
"language_code": "en"
}
Response
{
"success": true,
"keywords": [
{
"keyword": "seo tools",
"search_volume": 33100,
"competition": 0.67,
"cpc": 8.45,
"search_intent": "commercial",
"monthly_searches": [
{ "year": 2024, "month": 1, "search_volume": 33100 }
],
"categories": [10003]
}
]
}
AI Search Volume
Get AI search volume for keywords (ChatGPT, Gemini, etc.).
POST /api/keywords/ai-search-volume
Request Body
{
"keywords": ["best crm software", "project management tools"],
"location_code": 2840,
"language_code": "en"
}
Keywords for Keywords
Get related keywords sorted by relevance.
POST /api/keywords/for-keywords
Request Body
{
"keywords": ["seo", "content marketing"],
"location_code": 2840,
"language_code": "en",
"limit": 50
}
Categories for Keywords
Get DataForSEO category IDs for keywords.
POST /api/keywords/categories
Request Body
{
"keywords": ["seo tools", "marketing software"],
"location_code": 2840,
"language_code": "en"
}
Rankings
Track Rankings
Check SERP rankings for keywords (on-demand).
POST /api/rankings/track
Request Body
{
"keywords": [
{
"project_id": "proj_xyz789",
"keyword_text": "best seo tools",
"location_code": 2840,
"language_code": "en",
"device": "desktop",
"target_domain": "example.com",
"depth": 100
}
]
}
Response
{
"success": true,
"results": [
{
"keyword_id": "kw_abc123",
"keyword": "best seo tools",
"success": true,
"run_id": "run_xyz",
"results_count": 100,
"position": 7,
"matched_domain": "example.com",
"top_domains": [
{ "position": 1, "domain": "ahrefs.com", "url": "..." }
],
"cost": 0.0035
}
],
"total_keywords": 1,
"total_cost": 0.0035
}
Get Rankings
Retrieve stored rankings for a project.
GET /api/rankings?project_id={project_id}&keyword={keyword}&channel={channel}&limit={limit}
Query Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| project_id | string | Yes | Project ID |
| keyword | string | No | Filter by keyword (prefix match) |
| asset_id | string | No | Filter by asset |
| channel | string | No | seo, local, local_pack, app_store, apple_app_store, google_play_store |
| relationship | string | No | MINE, COMPETITOR, OTHER |
| limit | integer | No | Max results (default: 50, max: 200) |
Response
{
"rankings": [
{
"id": "serp_run123_7",
"keyword": "best seo tools",
"position": 7,
"previous_position": 9,
"change": 2,
"url": "https://example.com/seo-tools",
"domain": "example.com",
"title": "Best SEO Tools in 2024",
"platform": "google",
"channel": "seo",
"check_date": "2024-01-15",
"check_ts": "2024-01-15T10:30:00Z",
"asset_name": "My Website",
"relationship": "MINE",
"status": "ranked"
}
],
"count": 50,
"project_id": "proj_xyz789"
}
Apps
App Search
Search for apps to add as assets.
POST /api/apps/search
Request Body
{
"query": "spotify",
"platform": "apple",
"limit": 10
}
Response
{
"query": "spotify",
"platform": "apple",
"results": [
{
"app_id": "324684580",
"title": "Spotify - Music and Podcasts",
"platform": "apple",
"url": "https://apps.apple.com/app/id324684580",
"icon": "https://...",
"developer": "Spotify AB",
"rating": 4.8,
"reviews_count": 12500000,
"is_free": true,
"category": "Music"
}
],
"cost": 0.00144
}
Track App
Start tracking an app for rankings.
POST /api/apps/track
Request Body
{
"project_id": "proj_xyz789",
"app_id": "324684580",
"platform": "apple",
"name": "Spotify",
"icon_url": "https://...",
"url": "https://apps.apple.com/app/id324684580",
"frequency": "daily"
}
Response
{
"success": true,
"subscription": {
"id": "sub_abc123",
"project_id": "proj_xyz789",
"app_id": "324684580",
"platform": "apple",
"name": "Spotify",
"status": "active",
"frequency": "daily",
"next_run_at": "2024-01-16T10:30:00Z",
"tracking_enabled": true
},
"asset": {
"id": "asset_xyz",
"type": "app_ios",
"value": "324684580",
"name": "Spotify",
"role": "primary"
},
"orchestration": {
"type": "workflow",
"workflow_id": "wf_123",
"status_url": "/api/admin/workflow/app-details/wf_123"
}
}
Untrack App
DELETE /api/apps/untrack
Request Body
{
"project_id": "proj_xyz789",
"app_id": "324684580",
"platform": "apple"
}
List Apps
GET /api/apps?limit={limit}&offset={offset}
Get App Details
GET /api/apps/{app_id}
Response
{
"id": "324684580",
"platform": "apple",
"title": "Spotify - Music and Podcasts",
"subtitle": "Music and podcasts for everyone",
"developer_name": "Spotify AB",
"description": "With Spotify, you can...",
"rating": 4.8,
"rating_count": 12500000,
"price": 0,
"is_free": true,
"primary_category": "Music",
"icon_url": "https://...",
"screenshot_urls": ["https://..."],
"version": "8.9.10",
"size_bytes": 125829120,
"release_date": "2011-07-14",
"website_url": "https://spotify.com",
"created_at": 1705315800000,
"updated_at": 1705315800000
}
App Stats
GET /api/apps/{app_id}/stats
App Rankings
GET /api/apps/{app_id}/rankings
App Recommendations
GET /api/apps/{app_id}/recommendations
App All Rankings
Get combined category and recommendation rankings.
GET /api/app-store/apps/{app_id}/all-rankings
Domains
Top Domains
Get top-ranking domains.
GET /api/top-domains?limit={limit}
Domain Metrics
Get domain metrics from ClickHouse.
GET /api/domain-metrics?category_id={category_id}&limit={limit}
Admin Endpoints
Administrative endpoints for system management. Require additional admin permissions.
Domain Onboarding
Onboard Domain
Full domain onboarding with backlinks, keywords, and summary fetching.
POST /api/admin/domains/onboard
Request Body
{
"domain": "example.com",
"project_id": "proj_xyz789",
"asset_name": "Example Site",
"backlinks_limit": 1000,
"keywords_limit": 1000,
"skip_backlinks": false,
"skip_keywords": false,
"skip_referring_domains": false,
"location_code": 2840,
"language_code": "en"
}
Response
{
"success": true,
"domain": "example.com",
"domain_id": 123,
"orchestration": "workflow",
"workflow_id": "wf_abc123",
"status_url": "/api/admin/workflow/domain-onboard/wf_abc123",
"asset_id": "asset_xyz",
"project_id": "proj_xyz789",
"message": "Domain onboarding started via workflow orchestration."
}
Domain Status
GET /api/admin/domains/status?domain={domain}
Response
{
"domain": "example.com",
"domain_id": 123,
"data_tier": "customer",
"onboard_status": "completed",
"onboard_started_at": 1705315800000,
"onboard_completed_at": 1705315965000,
"fetch_timestamps": {
"backlinks_fetched_at": 1705315850000,
"keywords_fetched_at": 1705315900000,
"summary_fetched_at": 1705315920000
},
"stats": {
"backlinks": 5432,
"urls_total": 1200,
"urls_classified": 1150,
"keywords": 890,
"has_summary": true
},
"classification": {
"domain_type": "business",
"channel_bucket": "owned_media",
"classification_source": "llm",
"classification_confidence": 85
}
}
Classification Stats
URL Classification Stats
GET /api/admin/classification-stats?source={source}&domain_id={domain_id}
Response
{
"summary": {
"urls": {
"total": 125000,
"classified": 118500,
"crawled": 95000,
"avg_confidence": 78,
"low_confidence": 5200,
"high_confidence": 89000,
"coverage_pct": 95
},
"domains": {
"total": 45000,
"classified": 42000,
"typed": 38000,
"avg_confidence": 82,
"coverage_pct": 93
}
},
"distributions": {
"url_sources": [
{ "classification_source": "rules", "count": 85000 },
{ "classification_source": "llm", "count": 25000 }
],
"page_types": [
{ "page_type": "article", "count": 45000 },
{ "page_type": "product", "count": 22000 }
],
"confidence": [
{ "bucket": "90-100", "count": 65000 },
{ "bucket": "80-89", "count": 24000 }
]
}
}
Browse URLs
GET /api/admin/urls/browse?dimension={dimension}&value={value}&limit={limit}&offset={offset}
Query Parameters
| Parameter | Type | Description |
|---|---|---|
| dimension | string | page_type, quality_tier, domain_type, spam_tier, structural_type |
| value | string | Filter value (use "unknown" for unclassified) |
| search | string | URL search pattern |
| sort | string | recent, confidence, url |
| order | string | asc, desc |
| domain_id | integer | Filter by domain |
URL Feedback
Submit corrections for URL classifications.
POST /api/admin/urls/feedback
Request Body
{
"url_id": 12345,
"is_correct": false,
"corrected_page_type": "article",
"corrected_quality_tier": "high",
"corrected_structural_type": "blog_post",
"notes": "This is clearly a blog article"
}
Cost Tracking
Get Cost Summary
GET /api/admin/costs?since={since}&until={until}&minutes={minutes}
Daily Costs
GET /api/admin/costs/daily?days={days}&granularity={granularity}
Query Parameters
| Parameter | Type | Default | Description |
|---|---|---|---|
| days | integer | 30 | Number of days |
| granularity | string | day | minute, hour, day |
| project_id | string | - | Filter by project |
| service | string | - | Filter by service |
Run Costs
GET /api/admin/costs/run/{run_id}
Project Costs
GET /api/admin/costs/project/{project_id}
Comprehensive Summary
GET /api/admin/costs/summary
Queue Management
Queue Status
GET /api/admin/queues/status
Response
{
"summary": {
"active_queues": 4,
"total_queues": 5,
"total_messages": 1250,
"processing": 45,
"failed": 12,
"processed_today": 8500,
"rate_per_min": 142
},
"queues": [
{
"name": "domain-onboard",
"description": "Domain onboarding & enrichment",
"messages": 250,
"pending": 250,
"processing": 10,
"failed": 2,
"status": "processing",
"consumers": 3
}
]
}
Workflow Management
List Workflows
GET /api/admin/workflows
Running Workflows
GET /api/admin/workflows/running
Workflow History
GET /api/admin/workflows/history
Workflow Failures
GET /api/admin/workflows/failures
Get Workflow Status
GET /api/admin/workflow/{type}/{id}
Trigger Workflow
POST /api/admin/workflow/{type}
Pause Workflow
POST /api/admin/workflow/{type}/{id}/pause
Resume Workflow
POST /api/admin/workflow/{type}/{id}/resume
Terminate Workflow
DELETE /api/admin/workflow/{type}/{id}
Backlink Classifier
Trigger Classification
POST /api/admin/classifier/classify
Browse Classified URLs
GET /api/admin/classifier/browse
Brand Management
Populate Brands
POST /api/admin/populate-brands
Lock Brand
POST /api/admin/brands/{brand_id}/lock
Lock App Brand
POST /api/admin/apps/{app_id}/lock-brand
Assign Brand
POST /api/admin/apps/{app_id}/assign-brand
Cleanup Operations
Admin Cleanup
POST /api/admin/cleanup
Fix Primary Categories
POST /api/admin/fix-primary-categories
Fix Category IDs
POST /api/admin/fix-category-ids
Fix Games Categories
POST /api/admin/fix-games-categories
Data Migration
Migrate to ClickHouse
POST /api/admin/migrate-to-clickhouse
Webhook Endpoints
External callback handlers for third-party services.
DataForSEO App Info Webhook
Receives app details when DataForSEO tasks complete.
POST /api/dataforseo/app-info-webhook
Note: Called by DataForSEO service. Payload is gzip-compressed JSON.
DataForSEO App List Webhook
Receives app list results from DataForSEO.
POST /api/dataforseo/app-list-webhook
Pipeline Monitoring
Pipeline Activity
Get real-time pipeline activity stats.
GET /api/pipeline-activity?range={range}
Query Parameters
| Parameter | Type | Default | Description |
|---|---|---|---|
| range | string | 5m | Time range: 5m, 15m, 1h, 6h, 24h |
Response
{
"success": true,
"nodes": {
"classify-backlinks": {
"active": 5,
"currentQueued": 120,
"queuePending": 250,
"started": 1500,
"completed": 1450,
"failed": 15,
"successRate": 99,
"avgLatencyMs": 850
}
},
"uniqueItems": {
"urlsQueued": 5000,
"urlsClassified": 4850,
"keywordsQueued": 2000,
"keywordsClassified": 1920,
"domainsActive": 25
},
"timeRange": "5m",
"timestamp": "2024-01-15T10:30:00Z"
}
DAG Session Activation
Activate/deactivate DAG monitoring for real-time updates.
POST /api/dag-session/activate
DELETE /api/dag-session/activate
Internal Endpoints
Service-to-service APIs for internal operations.
Fetch Content
Fetch and parse webpage content.
POST /api/fetch-content
Request Body
{
"url": "https://example.com/page",
"extract_meta": true,
"max_text": 50000
}
Resolve Domain
Resolve www vs non-www domain before adding.
POST /api/util/resolve-domain
Request Body
{
"domain": "example.com"
}
Response
{
"input": "example.com",
"resolved": "www.example.com",
"redirected": true
}
Location Search
Search for DataForSEO location codes.
GET /api/locations/search?q={query}
Resolve Location
Resolve location name to location code.
POST /api/locations/resolve
Test Endpoints
Development and testing endpoints (require authentication).
Debug Auth
GET /test/debug-auth
Classifier Evaluation
GET /api/test/classifier-eval
POST /api/test/classifier-eval
Test DataForSEO
GET /api/test-dataforseo
Error Codes Reference
| Code | Endpoint Group | Description |
|---|---|---|
| 400 | All | Missing required parameters |
| 401 | All | Invalid or missing API key |
| 404 | Projects, Assets | Resource not found |
| 409 | Assets | Duplicate asset |
| 429 | All | Rate limit exceeded |
| 500 | All | Internal server error |
| 502 | DataForSEO | Upstream API error |
DataForSEO Response Structure
All DataForSEO proxy endpoints return this structure:
{
"tasks": [{
"result": [{
"items": [
{ /* actual data */ }
],
"total_count": 12345
}],
"cost": 0.01
}]
}
Standard parsing: data.tasks[0].result[0].items
Cost Reference
| Service | Endpoint | Cost |
|---|---|---|
| DataForSEO SERP | /serp/google/organic/live/advanced | $0.0035/request |
| DataForSEO Backlinks | /backlinks/summary/live | $0.02/request |
| DataForSEO Keywords | /dataforseo_labs/google/keyword_suggestions | $0.04/100 keywords |
| DataForSEO App List | /app_data/apple/app_listings/search/live | $0.00144/request |
| DataForSEO App Info | /app_data/apple/app_info/task_post | $0.015/app |
| Workers AI | Classification | $0.011/1K neurons |
| ZenRows | Web scraping | Plan-based |
SDK Examples
JavaScript/TypeScript
const response = await fetch('https://api.rankdisco.com/api/keywords/track', {
method: 'POST',
headers: {
'Authorization': 'Bearer YOUR_API_KEY',
'Content-Type': 'application/json'
},
body: JSON.stringify({
project_id: 'proj_xyz789',
keyword_text: 'best seo tools',
location_code: 2840,
language_code: 'en'
})
});
const data = await response.json();
console.log(data.keywords);
Python
import requests
response = requests.post(
'https://api.rankdisco.com/api/keywords/track',
headers={
'Authorization': 'Bearer YOUR_API_KEY',
'Content-Type': 'application/json'
},
json={
'project_id': 'proj_xyz789',
'keyword_text': 'best seo tools',
'location_code': 2840,
'language_code': 'en'
}
)
data = response.json()
print(data['keywords'])
cURL
curl -X POST https://api.rankdisco.com/api/keywords/track \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"project_id": "proj_xyz789",
"keyword_text": "best seo tools",
"location_code": 2840,
"language_code": "en"
}'