Studying a sire
The related horses give you a population to run through the statistics endpoints.
Documentation / Horses & pedigree
/v1/horses/{horse_id}/pedigree
Sire, dam and damsire, plus others by the same sire.
Send your key in the X-API-Key header, or as
?key= if your tool cannot set one. A date outside your plan's window returns
403 outside_window naming the window, never an empty array.
| Name | In | Type | Required | Description |
|---|---|---|---|---|
| horse_id | path | string | yes | Opaque horse identifier. |
curl https://api.apihorseracing.com/v1/horses/hs_V8JGH6/pedigree \ -H "X-API-Key: $AHR_KEY"
$ch = curl_init('https://api.apihorseracing.com/v1/horses/hs_V8JGH6/pedigree'); curl_setopt_array($ch, [ CURLOPT_RETURNTRANSFER => true, CURLOPT_HTTPHEADER => ['X-API-Key: ' . getenv('AHR_KEY')], ]); $data = json_decode(curl_exec($ch), true)['data'];
const res = await fetch( 'https://api.apihorseracing.com/v1/horses/hs_V8JGH6/pedigree', { headers: { 'X-API-Key': process.env.AHR_KEY } } ); const { meta, data } = await res.json();
import os, requests r = requests.get( "https://api.apihorseracing.com/v1/horses/hs_V8JGH6/pedigree", headers={"X-API-Key": os.environ["AHR_KEY"]}, ).json()
curl https://api.apihorseracing.com/v1/horses/hs_V8JGH6/pedigree?key=$AHR_KEY
$url = 'https://api.apihorseracing.com/v1/horses/hs_V8JGH6/pedigree' . '?key=$AHR_KEY'; $data = json_decode(file_get_contents($url), true)['data'];
const res = await fetch( 'https://api.apihorseracing.com/v1/horses/hs_V8JGH6/pedigree?key=$AHR_KEY' ); const { meta, data } = await res.json();
import os, requests r = requests.get( "https://api.apihorseracing.com/v1/horses/hs_V8JGH6/pedigree?key=$AHR_KEY", ).json()
{ "meta": { "request_id": "2bd134b5673bfd2d", "data_as_of": "2026-09-12T05:10:27+00:00", "plan": "analyst", "window": "2017 → upcoming", "note": "Breeding for this horse has not been fetched yet." }, "data": { "horse_id": "hs_V8JGH6", "name": "The Galloping Bear", "sex": "g", "colour": null, "pedigree": { "sire": null, "dam": null, "damsire": null, "status": "pending" } } }
A real response from /v1/horses/hs_V8JGH6/pedigree,
captured by calling the live API rather than written by hand.
Each field is described once and rendered on every endpoint that returns it, so the wording cannot drift between pages.
| Field | Type | What it is |
|---|---|---|
| horse_id | string | Opaque horse identifier. |
| name | string | Race title as published, sponsor and all. |
| Code | Status | When |
|---|---|---|
| unauthorized | 401 | No key, or one we do not recognise. Check the header name and that the key has not been rotated from your account page. |
| not_found | 404 | The identifier is well formed but nothing has it. Distinct from invalid_id, which means the identifier itself is wrong. |
| invalid_id | 422 | The prefix does not match the kind of thing the path expects, or the identifier is malformed. A horse id passed where a race is wanted lands here rather than returning the wrong race. |
| rate_limited | 429 | Past your per-minute rate. Retry-After is set, and X-RateLimit-Remaining tells you where you stand on every successful response too. |
| server_error | 500 | Ours, not yours. Every response carries a request_id; quote it and we can find the exact request. |
A real request from your browser straight to
api.apihorseracing.com with
your own key. Nothing is proxied and nothing is logged by this page.
Remembered in this browser so you do not paste it on every page. Forget it
Sire, dam and damsire, plus other horses in the archive by the same sire so you can see what a stallion actually produces rather than what he is said to produce.
Breeding records are keyed on the name rather than on a source identifier. The source's own identifiers for sire and dam were unusable: they repeated the subject horse's identifier on every record, which would have made every horse its own father. Keying on the name is imperfect where two stallions share one, and honest about being imperfect.
This pass runs behind the results crawl, so coverage is climbing. The field table below and /v1/meta/coverage both tell you where it has reached.
The related horses give you a population to run through the statistics endpoints.
Three generations is more than the source publishes; two is what exists.
A null sire means the pedigree pass has not reached this horse. It is not a statement that the breeding is unknown.