AlpacaKeep
Get early access
← All help articles
AdvancedFarm plan

Herd data for your web developer

Two read-only JSON addresses with the same animals the herd widget shows, for a developer who builds the farm's pages by hand. Fields, options, limits, rules.

This page is for the person who builds the farm's website. It is the long form of the For developers panel on the herd page in AlpacaKeep. If you are the farmer, the herd page article is the one you want.

Preview. Fields are only ever added, never renamed or removed. Tell us before you build something large on it.

What it is

Two read-only JSON addresses with the same data the herd widget shows. No key, no sign-up, callable straight from a browser (Access-Control-Allow-Origin: *). Use them when the widget's look is not close enough and you want to draw the herd yourself, or when each animal page on your site must be indexed by search engines. The widget is an iframe, so search engines read only the text of your own page around it; a page you render from this data is fully yours.

GET https://www.alpacakeep.com/api/public/v1/farm/<farm-slug>/herd
GET https://www.alpacakeep.com/api/public/v1/animal/<animal-slug>

The farmer has to switch this on first. It is off by default. In AlpacaKeep: Marketplace → Website widget → Set up the herd page → For developers → Turn on data access. Until then both addresses answer 404, while the widget keeps working.

The farm slug is shown in that panel. Every animal in the herd list carries its own slug; put that into the second address.

Options

AddressOptionMeaning
both?lang=en | it | deLanguage of the labels block and of sale_url. Default en.
herd?page=2100 animals per page. total is the whole herd.
herd?departed=1Include sold, transferred and deceased animals. Only has an effect when the farm switched that on.

Anything else in the query string is refused: an unknown option, the same option twice, or a value outside the table (page=0, page=51, page=02, lang=fr, departed=true) answers 400 with {"error":"bad_request"}. Do not add cache-busting parameters.

The herd list

{
  "version": 1,
  "farm": { "name": "Monviso Alpaca", "public_slug": "monviso", "country": "IT", "logo_url": null },
  "composition": [ { "stage": "breeding_f", "count": 14 }, { "stage": "stud", "count": 2 } ],
  "total": 31,
  "page": 1,
  "page_size": 100,
  "animals": [
    {
      "slug": "luna-7k3f9q",
      "name": "Luna",
      "show_name": "Monviso Luna",
      "display_name": "Monviso Luna",
      "species": "alpaca",
      "sex": "female",
      "dob": "2021-05-15",
      "life_stage": "breeding_f",
      "fiber_type": "Huacaya",
      "color_primary": "Light Fawn",
      "departed": null,
      "sale_url": null,
      "photo": { "src": "https://www.alpacakeep.com/_next/image?url=…&w=384&q=75", "srcset": "… 384w, … 640w, … 828w" }
    }
  ],
  "labels": {
    "life_stage": { "breeding_f": "Fattrici", "stud": "Stalloni", "…": "…" },
    "sex": { "male": "Maschio", "female": "Femmina", "unknown": "Sconosciuto" },
    "departed": { "moved": "Trasferito", "deceased": "Deceduto" }
  }
}
  • display_name is what to print: the registered name when there is one, else the name.
  • life_stage is one of cria_f, young_f, breeding_f, adult_f, cria_m, young_m, stud, adult_m, gelding, unknown (adult_f is an adult female the farm does not breed). Translate it through labels.life_stage; do not hard-code the words.
  • composition lists every stage in display order (zero counts included), ready for a legend or filter buttons. It counts the animals on this page, not the whole herd (total is the whole herd). For a herd of up to 100 animals the two are the same; past that, add the pages up yourself.
  • departed is null, "moved" or "deceased".
  • photo is null when the animal has none. Put src and srcset on an <img> together with a sizes attribute that matches your layout. The URLs are already resized and compressed; never link to anything else.
  • sale_url is the animal's public sale page when it is listed for sale, else null.

One animal

The answer is { "version": 1, "farm": { … }, "animal": { … }, "labels": { … } }, with farm and labels exactly as in the herd list. The animal object has everything a card has, plus:

{
  "bloodline": "Accoyo",
  "color_secondary": null,
  "markings": null,
  "eye_color": "brown",
  "height_cm": 90,
  "coi_percent": 3.1,
  "pedigree": {
    "sire": "Monviso Orion", "dam": "Monviso Nuvola",
    "paternal_grandsire": "Atlas", "paternal_granddam": "Stella",
    "maternal_grandsire": null, "maternal_granddam": null,
    "gen3": { "SSS": "Titan", "SSD": null, "SDS": null, "SDD": null, "DSS": null, "DSD": null, "DDS": null, "DDD": null }
  },
  "pedigree_colors": {
    "sire": "Light Fawn", "dam": "White",
    "paternal_grandsire": "Dark Brown", "paternal_granddam": null,
    "maternal_grandsire": null, "maternal_granddam": null,
    "gen3": { "SSS": null, "SSD": null, "SDS": null, "SDD": null, "DSS": null, "DSD": null, "DDS": null, "DDD": null }
  },
  "pedigree_colors_secondary": {
    "sire": "White", "dam": null,
    "paternal_grandsire": null, "paternal_granddam": null,
    "maternal_grandsire": null, "maternal_granddam": null,
    "gen3": { "SSS": null, "SSD": null, "SDS": null, "SDD": null, "DSS": null, "DSD": null, "DDS": null, "DDD": null }
  },
  "gallery": [ { "src": "https://…", "srcset": "…", "caption": null } ],
  "fiber_reports": [ { "date": "2026-05-01", "afd_micron": 19.4, "sd": 4.1, "cv": 21.1, "comfort_factor": 97.8, "spin_fineness": null, "curvature_deg_per_mm": null, "lab_name": "…", "coarse_edge_micron": 23.6, "staple_length_mm": 95 } ],
  "show_highlights": [ { "show_name": "National Show", "date": "2023-09-10", "show_end_date": "2023-09-11", "show_type": "halter", "class": "Huacaya female light", "colour_class": "Light", "sanctioning_body": "BAS", "placement_rank": 1, "entries_in_class": 9, "placing_status": null, "championship_award": "color_champion", "award_title": null, "score": null, "prize_type": "rosette", "ribbon_color": "blue", "placement": null, "photo_url": "https://…" } ]
}
  • pedigree.gen3 is the great-grandparents, keyed by the path from the animal: S = sire, D = dam, so SDS is the sire's dam's sire. null = unknown.
  • pedigree_colors has exactly the keys of pedigree and holds each ancestor's coat colour as the farm recorded it ("Light Fawn", "Medium Grey"). It is null when the ancestor is known only by name (typed in, not an animal on the farm) or has no colour recorded. Colour names are not translated. pedigree_colors_secondary has the same keys and holds the second colour of a two-coloured animal (null for a solid one); show the two together as "Light Fawn / White". Added October 2026.
  • coi_percent is the inbreeding coefficient in percent. It is null when it cannot be worked out from the recorded parents, or when the farm chose not to publish it.
  • fiber_reports is newest first, at most ten. It is an empty list when the farm chose not to publish fiber results; treat empty as "show nothing". Per report, any number may be null when the lab did not measure it:
    • afd_micron is the average fiber diameter and sd its spread, both in microns; cv is sd relative to afd_micron, in percent.
    • comfort_factor is the share of fibers at or under 30 microns, in percent. The share OVER 30 microns is 100 - comfort_factor; it is not a separate field, so work it out when you want to show it.
    • coarse_edge_micron (CEM) is the average diameter of the coarsest 5% of the fibers, in microns. staple_length_mm is the staple length the lab measured, in millimetres. Both added October 2026.
  • gallery excludes the profile photo (that one is photo).
  • show_highlights holds at most twelve results: the animal's STRONGEST, strongest first. Order: champion titles (Supreme Champion, Best in Show and Champion of Champions first, then Grand Champion, Best in Colour and Best of Breed, then Color, Age, Progeny and Performance Champion), then reserve titles (Reserve Supreme / Best in Show / Grand / Color Champion and the others), then other awards (Judge's Choice, Best Bred and Owned, Best Home-Country Bred, a specialty award) - each only when won in the animal's own class, a group class such as Get of Sire does not count - then the best placing, then the highest fleece score out of 100, then the newest date. Until September 2026 the list was newest first only, so do not assume the first result is the most recent: sort by date yourself if you need a timeline. The list is capped, so do not count results from it: an animal with a long show career has more than twelve. It is an empty list when the farm chose not to publish show results. Per result:
    • placement_rank is the class placing (1 = first) and entries_in_class the class size, either may be null.
    • placing_status is set only when there is no placing: "highly_commended", "not_placed", "withdrawn" or "disqualified".
    • championship_award is a title such as "color_champion", "grand_champion", "supreme_champion", "best_in_show" or a reserve ("reserve_color_champion", …), else null. It is the title's LEVEL; new values may be added over time (for example "age_champion", "best_in_colour", "progeny_champion", "performance_champion", their reserves, "reserve_best_in_show", "reserve_champion_of_champions", "best_bred_and_owned" and "best_home_country_bred"), so show an unknown value as a title rather than dropping the result.
    • award_title is the title exactly as the show printed it ("Beste Stute der Show", "Grand Champion White Male"), or null when the farm did not type one. When it is set, show it instead of a name for championship_award. It is only ever set beside a championship_award. One animal can hold several titles at one show: each is its own result.
    • score is a fleece score, normally out of 100 (fleece classes), else null. Some older records hold a score on another scale: write "/100" only beside a score between 0 and 100.
    • prize_type is what was handed over: "rosette", "ribbon", "sash", "trophy", "medal", "certificate", "plaque", "prize_money", "banner" or "other".
    • show_end_date is the last day of a show that ran over several days, null for a one-day show.
    • photo_url is the farm's own photo of this result (the rosette, the ring), already resized, or null.
    • placement is free text from older records; show it only when the fields above are empty. Class names, show names and placement are the farm's own words and are not translated.
  • Numbers are plain JSON numbers with a dot. Format them for your reader (19,4 in Italian and German).

What is never in it

Prices, availability, health tests (BVDV, DNA), pregnancy, notes, documents, registration numbers, purchase data, anything financial. If you need a price, link to sale_url.

Rules

  • Stable. version is 1. Fields are only ever added, never renamed or removed. Ignore keys you do not know. A list of values such as life_stage can gain a new value; show it with its word from labels.
  • Permanent animal slugs. An animal's slug never changes, and the animal address keeps answering after a sale, a transfer or a death (with departed set), so a printed QR code keeps working. It answers 404 with {"error":"not_found"} only when the farmer hides the animal, turns the herd page or the data access off, the farm's plan no longer includes the herd page, or the slug never existed. Handle a 404 and a 500 on your side: show your own page without the data rather than an error.
  • Five-minute cache. A change in AlpacaKeep can take up to five minutes to appear. Do not add a cache-busting parameter; cache on your side instead if you render on a server.
  • Fair use. Heavy automated traffic is slowed down per IP address, and we may switch data access off for a site that abuses it. One call per page view is fine; a loop over every animal on every page view is not: the herd list already carries what a grid needs.
  • Your visitors' privacy. If the page loads the data or the photos in the visitor's browser, as the example below does, the browser contacts AlpacaKeep directly and our servers see its IP address, just as with the website widget, so the site's privacy notice should mention it.
  • Credit. A page built on this data shows a visible link reading "Data by AlpacaKeep" to https://www.alpacakeep.com. The link may carry rel="nofollow". The marketplace listing terms apply to the farm.

Minimal example

<div id="herd"></div>
<script>
  fetch('https://www.alpacakeep.com/api/public/v1/farm/monviso/herd?lang=it')
    .then((r) => r.json())
    .then(({ animals, labels }) => {
      const el = document.getElementById('herd');
      for (const a of animals) {
        const card = document.createElement('a');
        card.href = '/gregge/' + a.slug;
        if (a.photo) {
          const img = document.createElement('img');
          img.src = a.photo.src;
          img.srcset = a.photo.srcset;
          img.sizes = '(min-width: 700px) 25vw, 50vw';
          img.alt = a.display_name;
          img.loading = 'lazy';
          card.appendChild(img);
        }
        card.appendChild(document.createTextNode(a.display_name + ' · ' + labels.life_stage[a.life_stage]));
        el.appendChild(card);
      }
    });
</script>
<a href="https://www.alpacakeep.com" rel="nofollow">Data by AlpacaKeep</a>

Related articles

Looking for something else?

Browse all help articles →