{"openapi": "3.0.0", "info": {"title": "WebAutomation Datasets API", "version": "1.0.0", "description": "One generic, schema-driven API over every WebAutomation dataset (G2, Amazon, Crunchbase, Trustpilot, Zillow, Similarweb, LinkedIn profiles/companies, YouTube, and more). List the datasets, read each one's field schema, then count, search, enrich, facet or aggregate \u2014 the same request shape works for all of them.\n\n**Authentication:** `Authorization: Bearer <api key>` \u2014 create keys under Account Settings \u2192 API Keys (`/account/settings/api-keys/`). The full key is shown exactly once at creation.\n\n**Billing:** every response (including errors) carries `credits_used` and `credits_remaining`. `datasets` (list), `schema`, `count`, `facets` and `aggregate` are **free**. `search` bills per record returned; `record` bills **1 credit on a match** (a miss is a free 404); `record/bulk` bills **per match**. Errors are never charged. The standard rate is 1 credit per result, but pricing is per plan \u2014 your exact per-endpoint costs are in `GET /v1/account` under `costs`.\n\n**Filters:** exact `{\"field\": \"value\"}`; range `{\"field\": {\"gt\": 3}}` (also `gte`, `lt`, `lte`, `min`, `max`); any-of `{\"field\": {\"in\": [\"a\", \"b\"]}}`; `ne`; `prefix`; `contains`; `exists`. Text fields are case-sensitive exact matches \u2014 use the example values from `GET /v1/datasets/{id}/schema`.\n\n**Rate limits are plan-based** (per-minute and per-day \u2014 read them from the `X-RateLimit-*` response headers). Exceeding them returns 429 with `Retry-After`."}, "servers": [{"url": "https://api.webautomation.io", "description": "Production API"}], "tags": [{"name": "Datasets API (v1)", "description": "Schema-driven access to every WebAutomation dataset. Free discovery (list/schema/count/facets/aggregate); search and enrich bill credits."}], "paths": {"/v1/account": {"get": {"tags": ["Datasets API (v1)"], "summary": "Account \u2014 plan, credits & limits (free)", "description": "Free. Returns your plan, remaining credits, per-endpoint costs and rate limits.", "operationId": "v1_account", "responses": {"200": {"description": "Account status.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"plan": "Starter", "credits": {"remaining": 4880}, "costs": {"dataset_search": 1}, "rate_limits": {"per_minute": 60, "per_day": 10000}}, "credits_used": 0, "credits_remaining": 4880}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}, "/v1/datasets": {"get": {"tags": ["Datasets API (v1)"], "summary": "List datasets (free)", "description": "Free. Lists every dataset available through the API with its id, name and record count. Use the id in the other endpoints.", "operationId": "v1_datasets_list", "responses": {"200": {"description": "The dataset catalog.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"count": 2, "datasets": [{"id": 344, "name": "G2.com Software Reviews Data", "records": 2705512, "countries_covered": null, "field_count": 18}, {"id": 672, "name": "Zillow Real Estate Agents Dataset", "records": 86200, "countries_covered": 1, "field_count": 16}]}, "credits_used": 0, "credits_remaining": 4880}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}, "/v1/datasets/{dataset_id}/schema": {"get": {"tags": ["Datasets API (v1)"], "summary": "Dataset schema \u2014 filterable fields (free)", "description": "Free. The dataset's customer-facing fields, their types, whether they're filterable, and an example value. Read this before filtering, sorting or aggregating.", "operationId": "v1_dataset_schema", "parameters": [{"name": "dataset_id", "in": "path", "required": true, "description": "Dataset id from GET /v1/datasets (e.g. 344 = G2 reviews, 672 = Zillow agents, 890 = YouTube profiles).", "schema": {"type": "integer"}, "example": 344}], "responses": {"200": {"description": "Field schema.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"id": 672, "name": "Zillow Real Estate Agents Dataset", "records": 86200, "fields": [{"name": "name", "type": "string", "filterable": true, "example": "Jane Doe"}, {"name": "total_sales", "type": "integer", "filterable": true, "example": 312}, {"name": "no_of_ratings", "type": "float", "filterable": true, "example": 4.9}]}, "credits_used": 0, "credits_remaining": 4880}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "404": {"description": "Dataset (or, for /record, the looked-up record) not found.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Dataset '999' not found. See GET /v1/datasets."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}, "/v1/datasets/{dataset_id}/count": {"post": {"tags": ["Datasets API (v1)"], "summary": "Count matching records (free)", "description": "Free. Total records in the dataset matching the filters. Cached ~5 minutes.", "operationId": "v1_dataset_count", "parameters": [{"name": "dataset_id", "in": "path", "required": true, "description": "Dataset id from GET /v1/datasets (e.g. 344 = G2 reviews, 672 = Zillow agents, 890 = YouTube profiles).", "schema": {"type": "integer"}, "example": 344}], "requestBody": {"required": false, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/DatasetCountRequest"}, "example": {"filters": {"product_rating": {"gt": 3}}}}}}, "responses": {"200": {"description": "Count.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"dataset": 699, "total": 48295}, "credits_used": 0, "credits_remaining": 4880}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "422": {"description": "Invalid filter, field, sort or operator.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Unknown filter 'foo'. See GET /v1/datasets/344/schema."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "404": {"description": "Dataset (or, for /record, the looked-up record) not found.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Dataset '999' not found. See GET /v1/datasets."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}, "/v1/datasets/{dataset_id}/search": {"post": {"tags": ["Datasets API (v1)"], "summary": "Search records (bills per record)", "description": "Returns records matching the filters, optionally sorted. Bills 1 credit per record returned (pre-authorized at per_page). Use sort + per_page for 'top N by field'.", "operationId": "v1_dataset_search", "parameters": [{"name": "dataset_id", "in": "path", "required": true, "description": "Dataset id from GET /v1/datasets (e.g. 344 = G2 reviews, 672 = Zillow agents, 890 = YouTube profiles).", "schema": {"type": "integer"}, "example": 344}], "requestBody": {"required": true, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/DatasetSearchRequest"}, "example": {"filters": {"category": "Books"}, "page": 1, "per_page": 5, "sort": "product_rating:desc"}}}}, "responses": {"200": {"description": "Records.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"dataset": 79, "total": 40005, "page": 1, "per_page": 5, "records": [{"product_name": "Example Book", "category": "Books", "product_rating": 4.8}]}, "credits_used": 5, "credits_remaining": 4875}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "402": {"description": "Not enough credits for this call.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Insufficient credits: this call can cost up to 25 credit(s) and you have 3. Lower per_page or top up at https://webautomation.io/pricing/."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "422": {"description": "Invalid filter, field, sort or operator.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Unknown filter 'foo'. See GET /v1/datasets/344/schema."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "404": {"description": "Dataset (or, for /record, the looked-up record) not found.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Dataset '999' not found. See GET /v1/datasets."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}, "/v1/datasets/{dataset_id}/record": {"get": {"tags": ["Datasets API (v1)"], "summary": "Enrich \u2014 one record by key (1 credit on match)", "description": "Look up the single best-matching record by one or more key fields passed as query params. The enrich key field is DATASET-SPECIFIC - look it up in GET /v1/datasets/{dataset_id}/schema (e.g. dataset 916 keys on `linkedin_url`, not `url`). This console offers the common keys (url, linkedin_url, domain) and a free-form `key` box for any other field name. 1 credit on a match; a miss is a free 404. LinkedIn URLs are matched regardless of scheme/case/trailing-slash.", "operationId": "v1_dataset_record", "parameters": [{"name": "dataset_id", "in": "path", "required": true, "description": "Dataset id from GET /v1/datasets (e.g. 344 = G2 reviews, 672 = Zillow agents, 890 = YouTube profiles).", "schema": {"type": "integer"}, "example": 344}, {"name": "url", "in": "query", "required": false, "description": "Key URL, for datasets whose key field is `url`. Matched regardless of scheme/case/trailing-slash.", "schema": {"type": "string"}, "example": "https://www.linkedin.com/in/some-person"}, {"name": "linkedin_url", "in": "query", "required": false, "description": "Key URL for datasets that key on `linkedin_url` instead of `url` (e.g. dataset 916). Matched regardless of scheme/case/trailing-slash.", "schema": {"type": "string"}, "example": "https://www.linkedin.com/in/some-person"}, {"name": "domain", "in": "query", "required": false, "description": "Key domain, for datasets whose key field is `domain`.", "schema": {"type": "string"}}, {"name": "key", "in": "query", "required": false, "description": "Any OTHER dataset-specific key field(s). The enrich key field varies by dataset - look it up in GET /v1/datasets/{dataset_id}/schema, then add it here as fieldName -> value (sent as ?fieldName=value). Use this when the dataset keys on a field other than url/linkedin_url/domain.", "style": "form", "explode": true, "schema": {"type": "object", "additionalProperties": {"type": "string"}}, "example": {}}], "responses": {"200": {"description": "The matched record.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"dataset": 916, "total": 1, "record": {"name": "Some Person", "linkedin_url": "https://www.linkedin.com/in/some-person"}}, "credits_used": 1, "credits_remaining": 4879}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "402": {"description": "Not enough credits for this call.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Insufficient credits: this call can cost up to 25 credit(s) and you have 3. Lower per_page or top up at https://webautomation.io/pricing/."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "404": {"description": "No matching record for the given key(s) (free).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["No matching record for the given key(s)."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "422": {"description": "Invalid filter, field, sort or operator.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Unknown filter 'foo'. See GET /v1/datasets/344/schema."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}, "/v1/datasets/{dataset_id}/record/bulk": {"post": {"tags": ["Datasets API (v1)"], "summary": "Bulk enrich \u2014 up to 100 keys (bills per match)", "description": "Match up to 100 values of one key field in a single call (the generic, any-dataset bulk enrich). 1 credit per match; misses are free. Results preserve input order; each item reports found.", "operationId": "v1_dataset_record_bulk", "parameters": [{"name": "dataset_id", "in": "path", "required": true, "description": "Dataset id from GET /v1/datasets (e.g. 344 = G2 reviews, 672 = Zillow agents, 890 = YouTube profiles).", "schema": {"type": "integer"}, "example": 344}], "requestBody": {"required": true, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/DatasetRecordBulkRequest"}, "example": {"field": "linkedin_url", "values": ["https://www.linkedin.com/in/person-a", "https://www.linkedin.com/in/person-b"]}}}}, "responses": {"200": {"description": "Per-value results.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"dataset": 916, "field": "linkedin_url", "requested": 2, "matched": 1, "results": [{"value": "https://www.linkedin.com/in/person-a", "found": true, "record": {"name": "Person A"}}, {"value": "https://www.linkedin.com/in/person-b", "found": false, "record": null}]}, "credits_used": 1, "credits_remaining": 4879}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "402": {"description": "Not enough credits for this call.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Insufficient credits: this call can cost up to 25 credit(s) and you have 3. Lower per_page or top up at https://webautomation.io/pricing/."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "422": {"description": "Invalid filter, field, sort or operator.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Unknown filter 'foo'. See GET /v1/datasets/344/schema."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "404": {"description": "Dataset (or, for /record, the looked-up record) not found.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Dataset '999' not found. See GET /v1/datasets."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}, "/v1/datasets/{dataset_id}/facets": {"get": {"tags": ["Datasets API (v1)"], "summary": "Facets \u2014 distinct values & counts (free)", "description": "Free. Distinct values and their counts for one or more fields (default 50, cap 500). Powers filter UIs and value discovery.", "operationId": "v1_dataset_facets", "parameters": [{"name": "dataset_id", "in": "path", "required": true, "description": "Dataset id from GET /v1/datasets (e.g. 344 = G2 reviews, 672 = Zillow agents, 890 = YouTube profiles).", "schema": {"type": "integer"}, "example": 344}, {"name": "field", "in": "query", "required": true, "description": "Field name(s) to facet (repeat for several).", "schema": {"type": "array", "items": {"type": "string"}}, "example": ["category"]}, {"name": "limit", "in": "query", "required": false, "description": "Max values per field (default 50, max 500).", "schema": {"type": "integer", "default": 50}}], "responses": {"200": {"description": "Facet buckets.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"dataset": 79, "facets": {"category": [{"value": "Books", "count": 40005}, {"value": "Electronics", "count": 22877}]}}, "credits_used": 0, "credits_remaining": 4880}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "422": {"description": "Invalid filter, field, sort or operator.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Unknown filter 'foo'. See GET /v1/datasets/344/schema."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "404": {"description": "Dataset (or, for /record, the looked-up record) not found.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Dataset '999' not found. See GET /v1/datasets."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}, "/v1/datasets/{dataset_id}/aggregate": {"post": {"tags": ["Datasets API (v1)"], "summary": "Aggregate \u2014 group-by stats (free)", "description": "Free. Group-by with metrics (count/avg/min/max/sum on numeric fields), with optional filters. Omit group_by for overall stats.", "operationId": "v1_dataset_aggregate", "parameters": [{"name": "dataset_id", "in": "path", "required": true, "description": "Dataset id from GET /v1/datasets (e.g. 344 = G2 reviews, 672 = Zillow agents, 890 = YouTube profiles).", "schema": {"type": "integer"}, "example": 344}], "requestBody": {"required": true, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/DatasetAggregateRequest"}, "example": {"group_by": "category", "metrics": [{"op": "count"}, {"op": "avg", "field": "product_rating"}], "limit": 5}}}}, "responses": {"200": {"description": "Grouped stats.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": true, "detail": [], "result": {"dataset": 79, "group_by": "category", "groups": [{"category": "Books", "count": 40005, "avg_product_rating": 4.3}]}, "credits_used": 0, "credits_remaining": 4880}}}}, "401": {"description": "Missing or invalid API key (revoked keys fail within ~5 minutes).", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Missing API key. Send it as 'Authorization: Bearer <your key>'."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "422": {"description": "Invalid filter, field, sort or operator.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Unknown filter 'foo'. See GET /v1/datasets/344/schema."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "404": {"description": "Dataset (or, for /record, the looked-up record) not found.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Dataset '999' not found. See GET /v1/datasets."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}, "429": {"description": "Rate limit exceeded.", "headers": {"X-RateLimit-Limit": {"description": "Your plan's per-minute request limit", "schema": {"type": "integer"}}, "X-RateLimit-Remaining": {"description": "Requests remaining in the current window", "schema": {"type": "integer"}}, "X-RateLimit-Reset": {"description": "Unix timestamp when the window resets", "schema": {"type": "integer"}}, "Retry-After": {"description": "Seconds to wait before retrying", "schema": {"type": "integer"}}}, "content": {"application/json": {"schema": {"$ref": "#/components/schemas/V1Envelope"}, "example": {"status": false, "detail": ["Rate limit exceeded. Retry after 30s."], "result": null, "credits_used": 0, "credits_remaining": 4880}}}}}}}}, "components": {"securitySchemes": {"V1BearerAuth": {"type": "http", "scheme": "bearer", "description": "Your API key as a Bearer token. Create one under Account Settings \u2192 API Keys."}}, "schemas": {"V1Envelope": {"type": "object", "description": "Standard response envelope used by every endpoint.", "properties": {"status": {"type": "boolean", "description": "true on success, false on error."}, "detail": {"type": "array", "items": {"type": "string"}, "description": "Human-readable messages (errors on failure)."}, "result": {"nullable": true, "description": "The endpoint-specific payload, or null on error."}, "credits_used": {"type": "integer", "description": "Credits charged for this call."}, "credits_remaining": {"type": "integer", "description": "Credits left after this call."}}}, "DatasetCountRequest": {"type": "object", "properties": {"filters": {"type": "object", "description": "Field\u2192value filters (see the Filters note).", "additionalProperties": true}}}, "DatasetSearchRequest": {"type": "object", "properties": {"filters": {"type": "object", "additionalProperties": true, "description": "Field\u2192value filters."}, "page": {"type": "integer", "default": 1, "minimum": 1}, "per_page": {"type": "integer", "default": 25, "minimum": 1, "maximum": 100}, "sort": {"type": "string", "nullable": true, "description": "'field:desc' or '-field'. Field must be in the schema."}, "fields": {"type": "array", "items": {"type": "string"}, "nullable": true, "description": "Subset of fields to return (defaults to all)."}}}, "DatasetAggregateRequest": {"type": "object", "properties": {"group_by": {"type": "string", "nullable": true, "description": "Field to group by (omit for overall stats)."}, "metrics": {"type": "array", "description": "Metrics to compute.", "items": {"type": "object", "properties": {"op": {"type": "string", "enum": ["count", "avg", "min", "max", "sum"]}, "field": {"type": "string", "description": "Numeric field (not needed for count)."}}}}, "filters": {"type": "object", "additionalProperties": true}, "limit": {"type": "integer", "default": 50, "description": "Max groups returned."}}}, "DatasetRecordBulkRequest": {"type": "object", "required": ["field", "values"], "properties": {"field": {"type": "string", "description": "The key field to match on (e.g. linkedin_url, url, domain)."}, "values": {"type": "array", "items": {"type": "string"}, "description": "Up to 100 values to look up."}}}}}, "security": [{"V1BearerAuth": []}]}