Datasets API endpoint
Searches public X (Twitter) user profiles stored in a search index. Sort enum: `relevance`, `followers_desc`, `followers_asc`, `crawled_at_desc`, `crawled_at_asc`, `created_at_desc`, `created_at_asc`. Billing: this search costs 1 credit per record returned, with a minimum of 2 (an empty result costs 2, a full page of 100 costs 100).
/datasets/x-users/searchSearches public X (Twitter) user profiles stored in a search index. Profiles are crawled from the logged-out public page (no login, no API key, no guest token); protected accounts are never indexed.
Dataset id enum:
x-usersQuery parameters:
q: optional full-text query over username, name, bio and location, max 256 characters.username: optional exact username filter (case-insensitive, leading @ stripped), max 128 characters.source_tier: optional exact filter for which seed tier discovered this account, e.g. github-users, wikidata, tiktok-creators, journalists. unknown covers records whose discovery tier was not recorded.is_blue_verified: optional filter for the X blue-check verification flag.has_bio: optional filter for a non-empty profile bio.has_external_url: optional filter for a linked external URL.min_followers: optional minimum follower count.max_followers: optional maximum follower count.min_ratio: optional minimum follower-to-following ratio, 0 or greater. Low values surface follow-spam / bot-like accounts.max_ratio: optional maximum follower-to-following ratio, 0 or greater.created_after: optional filter for accounts created on or after this date (RFC3339 or YYYY-MM-DD).created_before: optional filter for accounts created on or before this date (RFC3339 or YYYY-MM-DD).crawled_after: optional filter for records last refreshed on or after this date (RFC3339 or YYYY-MM-DD).crawled_before: optional filter for records last refreshed on or before this date (RFC3339 or YYYY-MM-DD).sort: optional sort enum: relevance, followers_desc, followers_asc, crawled_at_desc, crawled_at_asc, created_at_desc, created_at_asc.page: optional page number, defaults to 1.page_size: optional page size, defaults to 20 and maxes at 100.Response behavior:
relevance sort when q is supplied, otherwise followers_desc.crawled_at_asc returns the stalest records first; created_at_asc the oldest accounts first.min_followers must not exceed max_followers, and min_ratio must not exceed max_ratio.YYYY-MM-DD calendar date; other formats return the invalid params envelope.10000; page * page_size must not exceed 10000.items array (not an error) when the dataset has no matches yet.1 credit per record returned, minimum 2. A search that returns 20 records costs 20 credits, a full page of 100 costs 100, and an empty or one-record result costs 2. You are charged for what comes back, not for the page_size you ask for, but your balance must cover the requested page_size for the call to be accepted. The response header x-credit-cost shows what a call was charged.
| Field | Filled in, of 1 checked | Values in the sample |
|---|---|---|
| username | 1 | |
| id | 1 | |
| name | 1 | |
| bio | 1 | |
| location_raw | 1 | |
| external_url | 1 | gatesnot.es |
| avatar_url | 1 | pbs.twimg.com |
| banner_url | 1 | pbs.twimg.com |
| is_blue_verified | 1 | true in 1 of 1 |
| has_bio | 1 | true in 1 of 1 |
| has_external_url | 1 | true in 1 of 1 |
| followers | 1 | 64,723,215 |
| following | 1 | 571 |
| posts | 1 | 4,517 |
| follower_following_ratio | 1 | 113,350.64 |
| created_at | 1 | 2009-06-24 |
| source_tier | 1 | |
| crawled_at | 1 | 2026-08-16 |
| schema_version | 1 | |
| has_email | 1 | true in 0 of 1 |
| has_bio_url | 1 | true in 0 of 1 |
| is_default_profile_image | 1 | true in 0 of 1 |
| listed | 1 | 0 |
| media | 1 | 0 |
| likes | 1 | 0 |
| Parameter | Type | Required | Default | Description | Example |
|---|---|---|---|---|---|
| q | string | No | Full-text query over username, name, bio and location, max 256 characters | ||
| username | string | No | Exact username filter (case-insensitive), max 128 characters | ||
| source_tier | string | No | Exact filter for which seed tier discovered this account, e.g. github-users, wikidata, tiktok-creators, journalists | ||
| is_blue_verified | boolean | No | Filter by the X blue-check verification flag | ||
| has_bio | boolean | No | Filter by a non-empty profile bio | ||
| has_external_url | boolean | No | Filter by a linked external URL | ||
| min_followers | integer | No | Minimum follower count | ||
| max_followers | integer | No | Maximum follower count | ||
| min_ratio | number | No | Minimum follower-to-following ratio (low values surface follow-spam / bot-like accounts) | ||
| max_ratio | number | No | Maximum follower-to-following ratio | ||
| created_after | string | No | Accounts created on or after this date (RFC3339 or YYYY-MM-DD) | ||
| created_before | string | No | Accounts created on or before this date (RFC3339 or YYYY-MM-DD) | ||
| crawled_after | string | No | Records last refreshed on or after this date (RFC3339 or YYYY-MM-DD) | ||
| crawled_before | string | No | Records last refreshed on or before this date (RFC3339 or YYYY-MM-DD) | ||
| sort | string | No | Sort enum: relevance, followers_desc, followers_asc, crawled_at_desc, crawled_at_asc, created_at_desc, created_at_asc Allowed values: relevance, followers_desc, followers_asc, crawled_at_desc, crawled_at_asc, created_at_desc, created_at_asc. | ||
| page | integer | No | 1 | Page number, defaults to 1 | |
| page_size | integer | No | 20 and maxes at 100 | Page size, defaults to 20 and maxes at 100; page * page_size must be <= 10000 | |
| x-api-key (header) | string | Yes | API key required |
curl -X GET "https://api.crawlora.net/api/v1/datasets/x-users/search?q=coffee&is_blue_verified=true&has_bio=true&has_external_url=true&sort=relevance&page=1" \ -H "x-api-key: $CRAWLORA_API_KEY"
{
"code": 200,
"msg": "OK",
"data": {
"dataset": "x-users",
"items": [
{
"username": "octodev",
"name": "Octo Dev",
"bio": "Building things in public",
"location_raw": "Berlin, Germany",
"external_url": "https://octo.dev",
"avatar_url": "https://pbs.twimg.com/profile_images/example_normal.jpg",
"is_blue_verified": true,
"has_bio": true,
"has_external_url": true,
"followers": 12000,
"following": 800,
"posts": 3400,
"follower_following_ratio": 15,
"source_tier": "github-users",
"crawled_at": "2026-07-14T09:53:36Z",
"schema_version": 1
}
],
"page": 1,
"page_size": 20,
"total": 1,
"sort": "followers_desc"
}
}Request schema
No body schema
Response schema
#/definitions/datasets.xUsersSearchResponseDoc
| Field | Type | Required | Enum | Bounds | Example | Description |
|---|---|---|---|---|---|---|
| code | integer | No | 200 | |||
| data | datasets.XUserSearchResponse | No | ||||
| data.dataset | string | No | ||||
| data.items | array | No | ||||
| data.items[].avatar_url | string | No | ||||
| data.items[].banner_url | string | No | ||||
| data.items[].bio | string | No | ||||
| data.items[].bio_url_host | array | No | ||||
| data.items[].bio_urls | array | No | BioURLs are links written in the bio text, expanded from t.co. Distinct from ExternalURL (the single profile-header link). | |||
| data.items[].crawled_at | string | No | ||||
| data.items[].created_at | string | No | ||||
| data.items[].email | string | No | Email is an address the account self-published in its own bio. Extracted verbatim, never inferred or de-obfuscated. HasEmail is the faceting flag (an exists query on a keyword is fine, but a bool keeps parity with the other has_* fields and is cheaper to aggregate). | |||
| data.items[].external_url | string | No | ||||
| data.items[].follower_following_ratio | number | No | ||||
| data.items[].followers | integer | No | ||||
| data.items[].following | integer | No | ||||
| data.items[].has_bio | boolean | No | ||||
| data.items[].has_bio_url | boolean | No | ||||
| data.items[].has_email | boolean | No | ||||
| data.items[].has_external_url | boolean | No | ||||
| data.items[].id | string | No | ||||
| data.items[].is_blue_verified | boolean | No | ||||
| data.items[].is_default_profile_image | boolean | No | IsDefaultProfileImage marks never-customized shells. | |||
| data.items[].likes | integer | No | ||||
| data.items[].listed | integer | No | Listed is how many curated lists include the account -- the best authority proxy available. Media/Likes are activity signals. | |||
| data.items[].location_raw | string | No | ||||
| data.items[].media | integer | No | ||||
| data.items[].name | string | No | ||||
| data.items[].posts | integer | No | ||||
| data.items[].schema_version | integer | No | ||||
| data.items[].source_tier | string | No | ||||
| data.items[].username | string | No | ||||
| data.items[].verified_type | string | No | VerifiedType is the verification flavour ("Business", "Government", ...); empty for ordinary/blue accounts. | |||
| data.page | integer | No | ||||
| data.page_size | integer | No | ||||
| data.sort | string | No | ||||
| data.total | integer | No | ||||
| msg | string | No | OK |
| Status | Description | Schema |
|---|---|---|
| 400 | Bad Request | #/definitions/app.Response |
| 429 | Too Many Requests | #/definitions/app.Response |
| 500 | Internal Server Error | #/definitions/app.Response |
Use environment variables for secrets and keep Crawlora API keys server-side.
curl -X GET "https://api.crawlora.net/api/v1/datasets/x-users/search?q=coffee&is_blue_verified=true&has_bio=true&has_external_url=true&sort=relevance&page=1" \
-H "x-api-key: $CRAWLORA_API_KEY"