Guide

Chart a trend

How has Birmingham's population changed, and how does that compare with everywhere else? This guide builds a trend you can stand behind, including the moments the API stops you making a mistake.
  1. Read the measure

    Start by reading what the measure says about itself: its unit, whether it adds up, and which periods each of its sources covers. Here we'll use the local authority source on 2023 codes.

    curl "https://api.ukdataatlas.com/v1/measures/population"
    Example response200
    {
      "apiVersion": "v1",
      "atlasRelease": "sha256:5c4aa4529cbfbd5e4c844c55cddba1ef04a7bf76f3eaa085a357fff401af6d0c",
      "data": {
        "id": "population",
        "label": "Population estimate",
        "valueKind": "count",
        "unit": "people",
        "unitDefinition": {
          "code": "1",
          "scaleToCanonical": 1
        },
        "aggregation": {
          "kind": "extensive",
          "operation": "sum",
          "available": true
        },
        "sources": [
          {
            "datasetId": "population",
            "periods": [
              "2022"
            ],
            "sourceGeography": {
              "type": "ward",
              "boundaryYear": 2023
            },
            "coverage": {
              "kind": "partial",
              "countries": [
                "GB-ENG"
              ],
              "recordCount": 7608,
              "note": "Published source records are available for England and Wales only; this endpoint does not infer Scottish or Northern Irish values."
            }
          }
        ],
        "availability": {
          "sourceExact": true,
          "conversion": false,
          "aggregation": true
        },
        "links": {
          "data": "/v1/data/population"
        }
      },
      "meta": {
        "nextCursor": null
      }
    }
  2. Get the series

    Fetch every period for one area, oldest first, ready to plot. Each point in data.series has a period and a value.

    curl "https://api.ukdataatlas.com/v1/data/population/series?place=E08000025&geography=localAuthority&boundaryYear=2023"
    Example response200
    {
      "apiVersion": "v1",
      "atlasRelease": "sha256:5c4aa4529cbfbd5e4c844c55cddba1ef04a7bf76f3eaa085a357fff401af6d0c",
      "data": {
        "measure": {
          "id": "population",
          "label": "Population estimate",
          "valueKind": "count",
          "unit": "people",
          "aggregation": {
            "kind": "extensive",
            "operation": "sum",
            "available": true
          },
          "sources": [
            {
              "datasetId": "population",
              "periods": [
                "2022"
              ],
              "sourceGeography": {
                "type": "ward",
                "boundaryYear": 2023
              },
              "coverage": {
                "kind": "partial",
                "countries": [
                  "GB-ENG"
                ],
                "recordCount": 7608,
                "note": "Published source records are available for England and Wales only; this endpoint does not infer Scottish or Northern Irish values."
              }
            }
          ],
          "availability": {
            "sourceExact": true,
            "conversion": false,
            "aggregation": true
          },
          "links": {
            "data": "/v1/data/population"
          }
        },
        "source": {
          "datasetId": "population-uk",
          "periods": [
            "2011"
          ],
          "sourceGeography": {
            "type": "localAuthority",
            "boundaryYear": 2023
          },
          "coverage": {
            "kind": "source-reported",
            "countries": [
              "GB-ENG"
            ],
            "recordCount": 361,
            "note": "Published source records cover all four UK nations for every available period. Historic values remain keyed to the source's 2023 local-authority code vintage."
          }
        },
        "areaCode": "E08000025",
        "sourceGeography": {
          "type": "localAuthority",
          "boundaryYear": 2023
        },
        "provenance": {
          "atlasRelease": {
            "id": "sha256:5c4aa4529cbfbd5e4c844c55cddba1ef04a7bf76f3eaa085a357fff401af6d0c",
            "href": "/v1/atlas-release"
          },
          "measure": {
            "id": "population",
            "href": "/v1/measures/population"
          },
          "geography": {
            "source": {
              "type": "localAuthority",
              "boundaryYear": 2023
            },
            "match": {
              "status": "no-boundary-release-selected",
              "note": "The published observations declare a geography type and code vintage, but not a boundary release."
            }
          },
          "transformation": {
            "status": "not-applied",
            "note": "Values are served source-exact; no geographic conversion or aggregation was applied."
          },
          "source": {
            "dataset": {
              "id": "population-uk",
              "href": "/v1/datasets/population-uk"
            },
            "observations": {
              "artifact": "population-local-authority-observations",
              "contentHash": "sha256:1bf9e38cc9c37b37492b4a3cdc6b28c28ddeb5c2adc81e838ef947d78a0c0a9b",
              "periods": [
                "2011"
              ]
            }
          }
        },
        "series": [
          {
            "period": "2011",
            "areaCode": "E08000025",
            "value": 1074283,
            "status": "observed"
          }
        ]
      },
      "meta": {
        "nextCursor": null
      }
    }
  3. Put it in context

    A number on its own doesn't say much. Ask how Birmingham's growth from 2011 to 2022 ranks against every other local authority. The record gives its relativeChange and rank, and coverage.areasRanked says how many areas it was ranked against.

    curl "https://api.ukdataatlas.com/v1/data/population/change?geography=localAuthority&boundaryYear=2023&startPeriod=2011&endPeriod=2022&by=relative&place=E08000025"
    Example response200
    {
      "apiVersion": "v1",
      "atlasRelease": "sha256:24a500c55416bd7d58c28b1fc8cc4931d4a2fd831addafa3116556a91f2c4857",
      "data": {
        "startPeriod": "2011",
        "endPeriod": "2022",
        "change": {
          "direction": "end-minus-start",
          "basis": "relative",
          "order": "desc",
          "unit": "proportion",
          "interpretation": "Change in the source-published unit."
        },
        "coverage": {
          "areasRanked": 361,
          "areasWithBothPeriods": 361,
          "onlyAtStart": [],
          "onlyAtEnd": [],
          "withoutRelativeChange": 0
        },
        "records": [
          {
            "areaCode": "E09000001",
            "rank": 1,
            "tieCount": 1,
            "start": {
              "period": "2011",
              "areaCode": "E09000001",
              "value": 7412,
              "status": "observed"
            },
            "end": {
              "period": "2022",
              "areaCode": "E09000001",
              "value": 11615,
              "status": "observed"
            },
            "absoluteChange": 4203,
            "relativeChange": 0.567
          }
        ]
      },
      "meta": {
        "nextCursor": "RTA5MDAwMDAx"
      }
    }
  4. Know what not to do

    Some questions don't have a meaningful answer. A median house price can't be averaged across areas, so this is refused with aggregation_not_supported and an explanation:

    curl "https://api.ukdataatlas.com/v1/data/house-price-median/aggregate?period=2022&geography=ward&boundaryYear=2020&place=E92000001"
    Example response200
    {
      "apiVersion": "v1",
      "atlasRelease": "sha256:5c4aa4529cbfbd5e4c844c55cddba1ef04a7bf76f3eaa085a357fff401af6d0c",
      "data": {
        "measure": {
          "id": "population",
          "label": "Population estimate",
          "valueKind": "count",
          "unit": "people",
          "aggregation": {
            "kind": "extensive",
            "operation": "sum",
            "available": true
          },
          "sources": [
            {
              "datasetId": "population",
              "periods": [
                "2022"
              ],
              "sourceGeography": {
                "type": "ward",
                "boundaryYear": 2023
              },
              "coverage": {
                "kind": "partial",
                "countries": [
                  "GB-ENG"
                ],
                "recordCount": 7608,
                "note": "Published source records are available for England and Wales only; this endpoint does not infer Scottish or Northern Irish values."
              }
            }
          ],
          "availability": {
            "sourceExact": true,
            "conversion": false,
            "aggregation": true
          },
          "links": {
            "data": "/v1/data/population"
          }
        },
        "source": {
          "datasetId": "population-uk",
          "periods": [
            "2011"
          ],
          "sourceGeography": {
            "type": "localAuthority",
            "boundaryYear": 2023
          },
          "coverage": {
            "kind": "source-reported",
            "countries": [
              "GB-ENG"
            ],
            "recordCount": 361,
            "note": "Published source records cover all four UK nations for every available period. Historic values remain keyed to the source's 2023 local-authority code vintage."
          }
        },
        "period": "2022",
        "sourceGeography": {
          "type": "localAuthority",
          "boundaryYear": 2023
        },
        "area": {
          "id": "country/2025-12-uk-bgc/W92000004",
          "boundaryRelease": "2025-12-uk-bgc",
          "code": "W92000004",
          "name": "Wales",
          "aliases": [
            "Cymru"
          ]
        },
        "provenance": {
          "atlasRelease": {
            "id": "sha256:5c4aa4529cbfbd5e4c844c55cddba1ef04a7bf76f3eaa085a357fff401af6d0c",
            "href": "/v1/atlas-release"
          },
          "measure": {
            "id": "population",
            "href": "/v1/measures/population"
          },
          "geography": {
            "source": {
              "type": "localAuthority",
              "boundaryYear": 2023
            },
            "match": {
              "status": "no-boundary-release-selected",
              "note": "The published observations declare a geography type and code vintage, but not a boundary release."
            }
          },
          "transformation": {
            "status": "not-applied",
            "note": "Input observations are source-exact; no geographic conversion was applied."
          },
          "source": {
            "dataset": {
              "id": "population-uk",
              "href": "/v1/datasets/population-uk"
            },
            "observations": {
              "artifact": "population-local-authority-observations",
              "contentHash": "sha256:1bf9e38cc9c37b37492b4a3cdc6b28c28ddeb5c2adc81e838ef947d78a0c0a9b",
              "period": "2022"
            }
          }
        },
        "aggregation": {
          "operation": "sum",
          "membership": "gss-country-code",
          "inputRecordCount": 22,
          "coverage": {
            "status": "complete",
            "assessments": [
              {
                "boundaryRelease": "2023-05-uk-bgc-v2",
                "status": "complete",
                "expectedAreaCount": 22,
                "includedAreaCount": 22,
                "missingAreaCount": 0,
                "missingAreaSample": []
              }
            ],
            "href": "/v1/measures/population/coverage"
          },
          "note": "Country membership follows the first character of the GSS area code, which the coding scheme assigns by country."
        },
        "record": {
          "value": 3134196,
          "status": "derived"
        }
      },
      "meta": {
        "nextCursor": null
      }
    }

    Change is always measured within one set of area codes, so an area means the same place at the start and the end. Mixing in a boundary release is refused for the same reason.

  5. Quote the caveats

    Finally, fetch the measure's quality report. Each source has a coverage note, such as which nations are included, to show beside your chart.

    curl "https://api.ukdataatlas.com/v1/measures/population/quality"
    Example response200
    {
      "apiVersion": "v1",
      "atlasRelease": "sha256:5c4aa4529cbfbd5e4c844c55cddba1ef04a7bf76f3eaa085a357fff401af6d0c",
      "data": {
        "measure": {
          "id": "population",
          "valueKind": "count",
          "unit": "people",
          "aggregation": {
            "kind": "extensive",
            "operation": "sum",
            "available": true
          },
          "availability": {
            "sourceExact": true,
            "conversion": false,
            "aggregation": true
          }
        },
        "sources": [
          {
            "datasetId": "population",
            "sourceGeography": {
              "type": "ward",
              "boundaryYear": 2023
            },
            "sourceCoverage": {
              "kind": "partial",
              "countries": [
                "GB-ENG"
              ],
              "recordCount": 7608,
              "note": "Published source records are available for England and Wales only; this endpoint does not infer Scottish or Northern Irish values."
            },
            "boundaryCoverage": [
              {
                "boundaryRelease": "2023-05-uk-bgc",
                "title": "Wards, May 2023 (United Kingdom, generalised, clipped)",
                "coverageCountries": [
                  "GB-ENG"
                ]
              }
            ],
            "periods": [
              {
                "period": "2022",
                "artifact": "population-observations",
                "contentHash": "sha256:af1de02a052ace448dfb92c80cc312118a16c30bc77bf7a8c4d0e24a24ddab18",
                "recordCount": 7608,
                "statusCounts": {
                  "observed": 7608
                }
              }
            ]
          }
        ],
        "note": "Boundary coverage is code-set compatibility only. Status counts describe source observation records and do not impute missing areas."
      },
      "meta": {
        "nextCursor": null
      }
    }