Waterfall ICP Search
Tiered ICP contact waterfall. Checks tier 1 first, then 2, then 3, and stops when a tier returns contacts.
Endpoint
POST /api/v1/contacts/waterfall-icpAuthentication
All requests require the X-Satellyte-API-Key header. See Quickstart.
Request body
| Field | Type | Required | Notes |
|---|---|---|---|
company_domain | string | Conditional | Required if company_linkedin_url is absent. |
company_linkedin_url | string | Conditional | LinkedIn company URL. |
max_results | number | No | 1 to 25 contacts per matched tier. Defaults to 3. |
cascade | object[] | Yes | Ordered role tiers to try. Min 1, max 10. |
cascade[].role | string | Yes | Role label (decision_maker, budget_owner, influencer). |
cascade[].include_titles | string[] | Yes | Titles to include for this tier. |
cascade[].exclude_titles | string[] | No | Titles to exclude. |
cascade[].locations | string[] | No | Locations or WORLD. |
cURL
curl -i -X POST "https://api-staging.satellyte.ai/api/v1/contacts/waterfall-icp" \
-H "X-Satellyte-API-Key: $API_KEY" \
-H "Content-Type: application/json" \
-d '{
"company_domain": "stripe.com",
"company_linkedin_url": "https://www.linkedin.com/company/stripe",
"max_results": 3,
"cascade": [
{
"role": "decision_maker",
"include_titles": ["Chief Revenue Officer", "VP Sales", "Head of Sales"],
"exclude_titles": ["assistant", "intern", "junior"],
"locations": ["WORLD"]
},
{
"role": "budget_owner",
"include_titles": ["CEO", "Founder", "Co-Founder"],
"locations": ["WORLD"]
},
{
"role": "influencer",
"include_titles": ["Sales Manager", "Growth Manager", "RevOps"],
"locations": ["WORLD"]
}
]
}'Response (200)
{
"data": {
"matched": false,
"matched_tier": null,
"matched_role": null,
"items": [],
"waterfall": [
{
"tier": 1,
"role": "decision_maker",
"status": "not_matched",
"result_count": 0
},
{
"tier": 2,
"role": "budget_owner",
"status": "not_matched",
"result_count": 0
},
{
"tier": 3,
"role": "influencer",
"status": "not_matched",
"result_count": 0
}
]
}
}Response fields
| Field | Type | Notes |
|---|---|---|
matched | boolean | Whether any tier returned contacts. |
matched_tier | number | null | 1-indexed tier that produced results. |
matched_role | string | null | Role label of the matched tier. |
items[] | object[] | Contacts from the matched tier (same shape as /contacts/find). |
waterfall[] | object[] | Per-tier outcome. Each entry has tier, role, status (matched/not_matched), result_count. |
Error responses
All failed calls use the standard error envelope documented in Errors.
| Status | Code | Notes |
|---|---|---|
400 | validation_error | Returned when the request body is invalid, the company identifier is missing or invalid, cascade is missing or invalid, a tier is missing role or include_titles, or max_results is outside the supported range. |
401 | unauthorized | Returned when X-Satellyte-API-Key is missing, invalid, or expired. |
404 | not_found | Returned when Public API access is not enabled or the requested Public API resource is unavailable. |
429 | rate_limit_exceeded | Returned when the API key exceeds its configured rate limit. |
500 | service_error | Returned when the service cannot complete the request. Retry with backoff. |