/v1/candidate-searches
Send the brief — role, locations, skills, target count. Returns 202 with a search_id immediately. Idempotency-Key supported.
Send a hiring brief, get back an evidence-backed, ranked candidate shortlist from LinkedIn, Bayt, and trusted public sources. One POST to start, poll the status, read the candidates.
# Create a search — returns 202 with a search_id
curl -s -X POST "https://api.zenithr.example/v1/candidate-searches" \
-H "Authorization: Bearer zk_YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"role": "Senior Backend Engineer",
"locations": ["Dubai"],
"target_count": 20
}'
# Poll until "status" is "done"
curl -s "https://api.zenithr.example/v1/candidate-searches/SEARCH_ID" \
-H "Authorization: Bearer zk_YOUR_API_KEY"
import requests
r = requests.post(
"https://api.zenithr.example/v1/candidate-searches",
headers={"Authorization": "Bearer zk_YOUR_API_KEY"},
json={
"role": "Senior Backend Engineer",
"locations": ["Dubai"],
"target_count": 20,
},
)
search_id = r.json()["search_id"]
const res = await fetch(
"https://api.zenithr.example/v1/candidate-searches",
{
method: "POST",
headers: {
Authorization: "Bearer zk_YOUR_API_KEY",
"Content-Type": "application/json",
},
body: JSON.stringify({
role: "Senior Backend Engineer",
locations: ["Dubai"],
target_count: 20,
}),
},
);
const { search_id } = await res.json();
Sourcing runs asynchronously; candidates stream in while the search executes and every score carries its evidence.
/v1/candidate-searches
Send the brief — role, locations, skills, target count. Returns 202 with a search_id immediately. Idempotency-Key supported.
/v1/candidate-searches/{id}
Poll the run: stage, queries done, candidates found, spend so far. Or skip polling and register a signed webhook.
…/{id}/candidates
Read the ranked shortlist with per-criterion scoring evidence — or export it straight to CSV.
The details that make the difference between evaluating and shipping.
Terminal events delivered from a durable outbox, HMAC-signed with timestamped signatures.
Every response carries X-RateLimit headers; 429s come with Retry-After, never a mystery.
Retry a create with the same Idempotency-Key and get the original search back, not a duplicate.
One error envelope everywhere, and an X-Request-ID on every response for support.