Skip to content

Public API reference (v1)

The machine-readable OpenAPI 3.1 contract is served live at /api/v1/openapi.json — load it into Postman, Insomnia, or Swagger UI. This page is the human-facing companion: auth, credit billing, every endpoint, and real request/response examples.

  • Base URL: https://visibilityiq365.com/api/v1
  • Format: JSON in, JSON out. Success → { "success": true, "data": { … } } · Failure → { "success": false, "error": "<code>" }

Every /v1 endpoint requires a Bearer API key:

Authorization: Bearer viq_live_xxxxxxxxxxxxxxxxxxxxxxxx

Keys are minted in the dashboard at Developer API (/dashboard/developer). The secret is shown once at creation — only its SHA-256 hash is stored, so a lost key is regenerated, never recovered. Never embed a key in client-side code.

A request is rejected with 401 when the key is missing, malformed, unknown, or revoked; the auth chain never reveals which.

A key grants access only to the endpoint groups whose scope it holds. Scopes use resource:verb order (audits:read, not read:audits).

ScopeUnlocks
audits:readGET /v1/audits/{projectId}
rankings:readGET /v1/rankings/{projectId}, GET /v1/serp/overlay
keywords:readGET /v1/keywords, POST /v1/keywords/bulk
backlinks:readGET /v1/backlinks/{target}, POST /v1/backlinks/batch

A call whose key lacks the scope returns 403 {"error":"missing_scope:<scope>"}.


Each call costs max(base, perRow × rows) credits where rows is the requested page size (limit) or item count (seeds/targets). Own-data reads served from D1 cost 0. A failed request (4xx/5xx) is refunded — you are charged only on 200.

EndpointBasePer-rowEffective cost
GET /v1/audits/{projectId}000 (own data)
GET /v1/rankings/{projectId}000 (own data)
GET /v1/serp/overlay100 on cache hit, else 1
GET /v1/keywords51max(5, limit)
POST /v1/keywords/bulk011 × number of seeds
GET /v1/backlinks/{target}101max(10, limit)
POST /v1/backlinks/batch01010 × number of targets
TierMonthly creditsRate limitOverage
Starter5,00060 / min$1.00 / 1,000
Pro50,000120 / min$1.00 / 1,000
Agency250,000300 / min$0.75 / 1,000

Credits reset at the start of each calendar month.

HeaderMeaning
X-Credits-CostCredits charged for this request
X-Credits-RemainingCredits left in the current monthly period
X-RateLimit-Limit / X-RateLimit-RemainingPer-minute window state
Retry-AfterSeconds to wait before retrying (on 429 only)

StatusMeaning
400Invalid query or body (Zod validation)
401Missing / malformed / unknown / revoked key
402Credit budget exhausted (credit_exhausted)
403Key lacks the required scope (missing_scope:<scope>)
404Project or target not found, or not in the key’s organisation
429Rate limit exceeded (rate_limited; see Retry-After)
502Upstream data-provider error
503Data source not configured

Cross-tenant access returns 404, never 403, so a key cannot probe another organisation’s project IDs.


GET /v1/audits/{projectId} — latest audit summary

Section titled “GET /v1/audits/{projectId} — latest audit summary”

Scope audits:read · 0 credits. Returns the latest completed audit for a project in the key’s organisation.

Terminal window
curl https://visibilityiq365.com/api/v1/audits/uscoinshows \
-H "Authorization: Bearer $VIQ_KEY"
{
"success": true,
"data": {
"projectId": "uscoinshows",
"domain": "uscoinshows.com",
"audit": {
"id": "audit-1781524209869-wjp57j",
"status": "completed",
"score": 93,
"totalIssues": 16897,
"criticalIssues": 0,
"warnings": 727,
"notices": 16170,
"pagesCrawled": 5000,
"completedAt": "2026-06-15T13:32:06.473Z",
"createdAt": "2026-06-15T11:50:09.869Z"
}
}
}

audit is null when the project has no completed audit yet.


GET /v1/rankings/{projectId} — organic ranking keywords

Section titled “GET /v1/rankings/{projectId} — organic ranking keywords”

Scope rankings:read · 0 credits. Offset-paginated.

Query paramDefaultNotes
limit1001–1000 page size
offset0Row offset
positionMaxOnly keywords ranking at or above this position (1–100)
Terminal window
curl "https://visibilityiq365.com/api/v1/rankings/uscoinshows?limit=5&positionMax=20" \
-H "Authorization: Bearer $VIQ_KEY"
{
"success": true,
"data": {
"projectId": "uscoinshows",
"domain": "uscoinshows.com",
"total": 244,
"limit": 5,
"offset": 0,
"keywords": [
{
"keyword": "coin shows in texas",
"keywordHash": "e98288bc…",
"position": 1,
"previousPosition": null,
"positionChange": 0,
"searchVolume": 720,
"trafficEstimate": 216,
"intent": 0,
"serpFeaturesCount": 3,
"url": "https://www.uscoinshows.com/shows/tx",
"isBranded": false
}
]
}
}

intent: 0 informational · 1 navigational · 2 commercial · 3 transactional.
positionChange: current − previous (positive = dropped).
Paginate: loop offset += limit until offset ≥ total.


Scope keywords:read · max(5, limit) credits. Powered by VisibilityIQ’s keyword intelligence.

Query paramDefaultNotes
seed— (required)2–120 characters
databaseusLocale code
limit1001–1000 ideas
Terminal window
curl "https://visibilityiq365.com/api/v1/keywords?seed=coin%20show&limit=5" \
-H "Authorization: Bearer $VIQ_KEY"
{
"success": true,
"data": {
"seed": "coin show",
"database": "us",
"count": 5,
"keywords": [
{
"keyword": "pcgs coin grading",
"searchVolume": 22200,
"cpc": 2.27,
"keywordDifficulty": 61,
"competition": "LOW",
"intent": "informational"
}
]
}
}

Response headers on this call: X-Credits-Cost: 5, X-Credits-Remaining: 4995.


POST /v1/keywords/bulk — keyword ideas for many seeds

Section titled “POST /v1/keywords/bulk — keyword ideas for many seeds”

Scope keywords:read · 1 credit per seed.

Terminal window
curl -X POST https://visibilityiq365.com/api/v1/keywords/bulk \
-H "Authorization: Bearer $VIQ_KEY" \
-H "Content-Type: application/json" \
-d '{"seeds":["coin show","rare coins"],"database":"us","limitPerSeed":3}'

Body: seeds (1–100 strings), database (default us), limitPerSeed (1–200, default 50).

{
"success": true,
"data": {
"database": "us",
"seedCount": 2,
"results": [
{ "seed": "coin show", "count": 3, "keywords": [ "…same shape as /keywords…" ] },
{ "seed": "rare coins", "count": 3, "keywords": [] }
]
}
}

Section titled “GET /v1/backlinks/{target} — backlink profile”

Scope backlinks:read · max(10, limit) credits. target is a URL-encoded domain or URL.

Terminal window
curl "https://visibilityiq365.com/api/v1/backlinks/uscoinshows.com?limit=50" \
-H "Authorization: Bearer $VIQ_KEY"

Returns { target, summary:{referringDomains,backlinks,dfsRank}, authority:{calibrated,components}, referringDomains:[{domain,domainAuthority,dofollow,backlinks}] }.


POST /v1/backlinks/batch — backlink summaries for many targets

Section titled “POST /v1/backlinks/batch — backlink summaries for many targets”

Scope backlinks:read · 10 credits per target.

Body: targets (1–25 strings), limitPerTarget (1–1000, default 100).


GET /v1/serp/overlay — per-URL SERP metrics

Section titled “GET /v1/serp/overlay — per-URL SERP metrics”

Scope rankings:read · 0 credits on cache hit (else 1). Powers the browser-extension overlay.

Query paramNotes
urlRequired — the page to look up
projectIdRequired — the project that owns the rankings

Returns { url, domain, keywords:[{keyword,position,volume,ctr,impressions,estimatedTraffic}], topKeyword, estimatedTraffic, crawlStatus } for the URL’s top 5 ranking keywords. Returns 200 with an empty keywords array when the domain has no ranking data yet.


Public, no auth. The full OpenAPI 3.1 document — load into Swagger UI, Postman, or Insomnia.


Terminal window
export VIQ_KEY="viq_live_…" # from /dashboard/developer (shown once at creation)
BASE="https://visibilityiq365.com/api/v1"
# Free own-data reads:
curl "$BASE/audits/<projectId>" -H "Authorization: Bearer $VIQ_KEY"
curl "$BASE/rankings/<projectId>?limit=100&positionMax=10" -H "Authorization: Bearer $VIQ_KEY"
# Metered keyword research (watch X-Credits-Remaining):
curl "$BASE/keywords?seed=your%20topic&limit=20" -H "Authorization: Bearer $VIQ_KEY"

Pagination: loop offset += limit until offset ≥ data.total.
Rate limits: on 429, sleep Retry-After seconds and retry.
Budget: watch X-Credits-Remaining; 402 means the monthly budget is spent — upgrade or wait for the reset.