Use Case
Search company records with guarded OpenSearch Query DSL. Discover valid fields first, inspect top values for one field, then run the paginated search.
Recommended Flow
GET /search/filter-capabilities
POST /search/filter-field-values
POST /search/start-filter-search
| Name | Type | Required | Description |
|---|
x-api-key | string | Yes | Your Sixtyfour API key. |
Content-Type | string | For POST requests | Must be application/json. |
Filter Capabilities
GET https://api.sixtyfour.ai/search/filter-capabilities
Returns the live field contract for company direct-filter search.
Use value_fields to determine which fields support POST /search/filter-field-values.
value_fields entry
| Field | Type | Description |
|---|
field | string | Canonical field name to use in API requests. |
aggregation_field | string or null | Underlying field used for top-values aggregation. |
nested_path | string or null | Nested path for nested fields. |
value_type | string | Mapping-derived value type such as keyword, boolean, number, or date. |
supports_top_values | boolean | Whether POST /search/filter-field-values supports this field. |
supports_exact_filter_snippet | boolean | Whether the response can include deterministic exact-match snippets. |
Field Values
POST https://api.sixtyfour.ai/search/filter-field-values
Returns top values for one field, ranked by descending scoped company count. There is no batch variant.
Request Body
| Field | Type | Required | Description |
|---|
mode | string | No | Must be "company". Defaults to "company". |
field | string | Yes | Field to inspect. The field must exist in value_fields and support top values. |
top_k | integer | No | Number of values to return. Range 1..100. Default 25. |
filters | object | No | Optional scoped query. Only filters.query is allowed. |
Scoped Query
- Omit
filters for global scope.
- Send only
filters.query for scoped discovery.
filters.sort and filters.size are not allowed on this endpoint.
{
"filters": {
"query": { "...": "..." }
}
}
Request Example
Global:
{
"mode": "company",
"field": "hq_country_iso2",
"top_k": 10
}
Scoped:
{
"mode": "company",
"field": "industry",
"top_k": 20,
"filters": {
"query": {
"bool": {
"filter": [
{ "term": { "hq_country_iso2": "US" } },
{ "range": { "employees_count": { "gte": 200, "lte": 5000 } } },
{ "term": { "ownership_status": "private" } }
]
}
}
}
}
Response
{
"mode": "company",
"field": "hq_country_iso2",
"canonical_field": "hq_country_iso2",
"aggregation_field": "hq_country_iso2",
"nested_path": null,
"value_type": "keyword",
"supports_top_values": true,
"supports_exact_filter_snippet": true,
"total_scoped_documents": 12345,
"request_duration_ms": 47,
"values": [
{
"value": "US",
"count": 4200,
"percent_of_scope": 0.340219,
"filter_snippet": {
"term": { "hq_country_iso2": "US" }
}
}
]
}
Response Fields
| Field | Type | Description |
|---|
mode | string | Always "company". |
field | string | Field requested in the request. |
canonical_field | string | Canonical field resolved by the server. |
aggregation_field | string or null | Actual field aggregated in OpenSearch. |
nested_path | string or null | Nested path for nested fields. |
value_type | string | Mapping-derived value type. |
supports_top_values | boolean | Capability flag for this field. |
supports_exact_filter_snippet | boolean | Whether exact snippet generation is available. |
total_scoped_documents | integer | Number of company documents in the active scope. |
request_duration_ms | integer | Server processing time in milliseconds. |
values | array | Top values ranked by descending count in the active scope. |
values entry
| Field | Type | Description |
|---|
value | any or null | Candidate value. |
count | integer | Company-document count for this value inside the active scope. |
percent_of_scope | number | count / total_scoped_documents, rounded to 6 decimals. |
filter_snippet | object or null | Ready-to-use exact filter clause for this value. |
Nested Example
For nested fields such as funding_rounds.name, counts are company-document counts and snippets are wrapped in nested.
{
"field": "funding_rounds.name",
"values": [
{
"value": "Series A",
"count": 120,
"percent_of_scope": 0.15,
"filter_snippet": {
"nested": {
"path": "funding_rounds",
"query": {
"term": { "funding_rounds.name.keyword": "Series A" }
}
}
}
}
]
}
Error Codes
| HTTP | code | Meaning |
|---|
400 | unsupported_mode | mode is not company. |
400 | invalid_scoped_filters | Scoped body is invalid. This includes missing filters.query or unsupported keys. |
400 | unsupported_field | Field is not supported for value discovery. |
400 | top_values_not_supported | Field exists but does not support top-values aggregation. |
400 | invalid_request | Generic request validation failure. |
504 | opensearch_timeout | Aggregation timed out. Retry with narrower scope or smaller top_k. |
500 | aggregation_failed | Unexpected aggregation failure. |
Start Filter Search
POST https://api.sixtyfour.ai/search/start-filter-search
Runs the paginated company search. Use filter_snippet values from POST /search/filter-field-values to build exact filters.
Request Body
| Field | Type | Required | Description |
|---|
mode | string | No | Defaults to "company". Only company mode is supported. |
filters | object | Conditionally | Required for fresh searches. Must include query. Optional sort, optional size. |
max_results | integer | No | Total cap across pages. Range 1..5000. |
page_size | integer | No | Page size for company pagination. Range 1..100. Default 10. |
cursor | string | No | Cursor token for the next page. When present, the request should only include cursor. |
save_json | boolean | No | Not supported for company mode. true returns 400. |
Request Flow
- First request: send
filters and optionally page_size and max_results.
- Next page request: send only
{"cursor":"..."}.
- Requests that mix
cursor with filters, page_size, max_results, or save_json are invalid.
Effective Result Cap
page_size controls rows per page. Range 1..100. Default 10.
max_results controls the row cap across all pages. Range 1..5000.
- If
max_results is omitted, the effective cap can come from filters.size.
- If both
max_results and filters.size are omitted, the backend applies its default server cap flow.
Request Example
First page:
{
"mode": "company",
"page_size": 10,
"max_results": 100,
"filters": {
"query": {
"bool": {
"filter": [
{ "term": { "hq_country_iso2": "US" } },
{ "range": { "employees_count": { "gte": 100, "lte": 5000 } } }
]
}
},
"sort": [
{ "employees_count": "desc" }
]
}
}
Next page:
{
"cursor": "eyJpZCI6I..."
}
Response
{
"next_cursor": "eyJpZCI6I...",
"cursor_expires_in_seconds": 1800,
"request_duration_ms": 142,
"has_more": true,
"page_size": 10,
"page_count": 10,
"page_number": 1,
"max_pages": 500,
"remaining_results": 4990,
"total_results": 10,
"exported_count": 0,
"results": [
{
"raw_document_id": "stripe",
"raw_source": {
"company_name": "Stripe",
"hq_country_iso2": "US",
"employees_count": 8000
}
}
]
}
| Field | Type | Description |
|---|
next_cursor | string or null | Cursor for the next page. null when there are no more pages. |
cursor_expires_in_seconds | integer | Seconds until the current cursor expires. |
request_duration_ms | integer | Server-side request duration in milliseconds. |
has_more | boolean | Whether another page is available. |
page_size | integer | Requested page size. |
page_count | integer | Number of rows returned in the current page. |
page_number | integer | Current page number, starting at 1. |
max_pages | integer | Maximum page count available under the effective cap for this search. |
remaining_results | integer | Number of rows still available under the effective cap after the current page. |
total_results | integer | Cumulative rows returned so far across the cursor flow. This is not a global match count. |
exported_count | integer | Always 0 in company mode. |
results | array | Company rows for the current page. |
Result Row
| Field | Type | Description |
|---|
raw_document_id | string | Stable identifier for the returned company document. |
raw_source | object | Company source payload for the row, excluding hidden internal fields. |
{
"raw_document_id": "stripe",
"raw_source": {
"company_name": "Stripe",
"hq_country_iso2": "US",
"employees_count": 8000
}
}
raw_source returns the company document directly. It does not use grouped objects such as identity, profile, or location.
Error Response
| Status | Description |
|---|
400 | Invalid or expired cursor, invalid Query DSL, unsupported parameters, unsupported mode, save_json=true in company mode, invalid page_size, or invalid max_results. |
404 | Cursor belongs to another organization. |
409 | Cursor is already being processed. Retry with the same cursor after the in-flight request finishes. |
429 | Rate limit exceeded. |
500 | Unexpected server error. |
503 | Company OpenSearch is not configured. |
Example 400 response:
{
"detail": "Cursor is invalid or has expired"
}
Filters
The filters object accepts OpenSearch Query DSL for company records.
Top-Level Shape
{
"filters": {
"query": { ... },
"sort": [ ... ],
"size": 100
}
}
| Key | Type | Description |
|---|
query | object | Required for fresh searches. OpenSearch query object. |
sort | array | Optional. Sort clauses for the first request. |
size | integer | Optional. Additional size hint that can drive the effective cap when max_results is omitted. |
Supported Query Clauses
| Clause | Description |
|---|
bool | Combine conditions with must, filter, should, and must_not. |
term | Exact-match query for a single value. |
terms | Exact-match query for multiple values. |
range | Numeric or date range with gt, gte, lt, lte. |
exists | Match documents where a field is present. |
match | Full-text match query. |
match_phrase | Phrase query. |
multi_match | Search the same value across multiple fields. |
nested | Query nested arrays and nested objects. |
match_all | Match all company records. |
Use GET /search/filter-capabilities to determine valid query, sort, range, nested, and value fields.
Query Examples
Exact match:
{
"term": {
"website_domain": "stripe.com"
}
}
Range filter:
{
"range": {
"employees_count": {
"gte": 100,
"lte": 5000
}
}
}
Multi-field full-text search:
{
"multi_match": {
"query": "cloud security",
"fields": [
"description",
"categories_and_keywords.element"
],
"type": "best_fields",
"operator": "and"
}
}
Nested query:
{
"nested": {
"path": "funding_rounds",
"query": {
"match_phrase": {
"funding_rounds.name": "Series B"
}
}
}
}
Limits
| Limit | Value |
|---|
POST /search/filter-field-values | 20 requests per minute per organization |
POST /search/start-filter-search | 10 requests per minute per organization |
top_k | 1..100 |
page_size | 1..100 |
max_results | 1..5000 |