Why
PolicyEngine/policyengine-uk#1896 replaces the generic is_child (age < 18) and is_adult (age >= 18) flags inside the UK model with each programme's legal definition and adds HBAI variables (is_hbai_dependent_child, is_hbai_adult, hbai_person_type). The generic variables stay as deprecated shims with their old formulas, so nothing in uk-data breaks. But each uk-data use should read the definition of the statistic it targets; age < 18 matches none of them. Separately, uk-data can now supply the exact HBAI dependent-child flag.
1. Supply is_hbai_dependent_child from the FRS
The FRS child table is exactly the HBAI dependent-child population. frs.py already separates adult and child records to derive is_parent (derive_is_parent_from_frs_microdata). Add pe_person["is_hbai_dependent_child"] = ~np.isin(person_id, frs["adult"].person_id). Once the dataset carries it, the model's claimant/partner and couple classification use the survey's own benefit-unit roles instead of the calculator fallback (which, for example, cannot tell a 16- or 17-year-old partner from a dependant). Add a test that every benefit unit has one or two non-dependants.
2. Calibration targets (currently computed with age < 18)
calibration/matrix_builder.py:127-136, datasets/local_areas/constituencies/loss.py:107-118, targets/compute/benefits.py:33-51 (UC households by number of children): Stat-Xplore counts children and young people under 20 declared in the UC household. Use is_child_or_qualifying_young_person_for_universal_credit (or an explicit (age < 20) & ~is_uc_claimant predicate named for the statistic).
targets/compute/benefits.py:54-99 (UC by family type and payment band): children as above; "couple" is a UC joint claim (is_couple, now the claimant-has-a-partner test), not "two people aged 18+" (family_type, deprecated).
targets/compute/benefits.py:114-163, targets/dwp.py:200-305 (two-child limit): use is_child_or_qualifying_young_person_for_universal_credit; change the Target metadata from is_child.
targets/compute/benefits.py:24-30 (Scotland UC with a child under 1): age < 1 alone.
targets/compute/demographics.py:71-76 and targets/compute/households.py:6-51 (census and ONS household types): the ONS/census dependent child is under 16, or 16-18 in full-time education with no partner or child in the household. Use a predicate named for that source, and build household types from it, not from family_type.
create_target_matrix catches exceptions and logs "Skipping target": add a test that fails if any registered target is skipped, so a broken predicate cannot silently drop targets.
3. Imputation predictors
- ETB public services (
imputations/services/etb.py) and VAT (imputations/vat.py): ETB's own child definition is the HBAI dependent child, so predict from household counts of is_hbai_dependent_child and is_hbai_adult, and use household_count_people as the per-person divisor. Retrain the cached models.
- LCFS consumption (
imputations/consumption.py) and WAS wealth (imputations/wealth.py): keep results with explicit age counts computed in uk-data (the LCF and WAS definitions differ; flag the gap) instead of the deprecated is_child/is_adult/num_children/num_adults.
- Capital gains (
imputations/capital_gains.py): adult_index (now explicitly "rank among household members aged 18 or over") is unchanged; switch to is_household_head if the reference person is intended.
🤖 Generated with Claude Code
Why
PolicyEngine/policyengine-uk#1896 replaces the generic
is_child(age < 18) andis_adult(age >= 18) flags inside the UK model with each programme's legal definition and adds HBAI variables (is_hbai_dependent_child,is_hbai_adult,hbai_person_type). The generic variables stay as deprecated shims with their old formulas, so nothing in uk-data breaks. But each uk-data use should read the definition of the statistic it targets; age < 18 matches none of them. Separately, uk-data can now supply the exact HBAI dependent-child flag.1. Supply
is_hbai_dependent_childfrom the FRSThe FRS child table is exactly the HBAI dependent-child population.
frs.pyalready separates adult and child records to deriveis_parent(derive_is_parent_from_frs_microdata). Addpe_person["is_hbai_dependent_child"] = ~np.isin(person_id, frs["adult"].person_id). Once the dataset carries it, the model's claimant/partner and couple classification use the survey's own benefit-unit roles instead of the calculator fallback (which, for example, cannot tell a 16- or 17-year-old partner from a dependant). Add a test that every benefit unit has one or two non-dependants.2. Calibration targets (currently computed with age < 18)
calibration/matrix_builder.py:127-136,datasets/local_areas/constituencies/loss.py:107-118,targets/compute/benefits.py:33-51(UC households by number of children): Stat-Xplore counts children and young people under 20 declared in the UC household. Useis_child_or_qualifying_young_person_for_universal_credit(or an explicit(age < 20) & ~is_uc_claimantpredicate named for the statistic).targets/compute/benefits.py:54-99(UC by family type and payment band): children as above; "couple" is a UC joint claim (is_couple, now the claimant-has-a-partner test), not "two people aged 18+" (family_type, deprecated).targets/compute/benefits.py:114-163,targets/dwp.py:200-305(two-child limit): useis_child_or_qualifying_young_person_for_universal_credit; change the Target metadata fromis_child.targets/compute/benefits.py:24-30(Scotland UC with a child under 1):age < 1alone.targets/compute/demographics.py:71-76andtargets/compute/households.py:6-51(census and ONS household types): the ONS/census dependent child is under 16, or 16-18 in full-time education with no partner or child in the household. Use a predicate named for that source, and build household types from it, not fromfamily_type.create_target_matrixcatches exceptions and logs "Skipping target": add a test that fails if any registered target is skipped, so a broken predicate cannot silently drop targets.3. Imputation predictors
imputations/services/etb.py) and VAT (imputations/vat.py): ETB's own child definition is the HBAI dependent child, so predict from household counts ofis_hbai_dependent_childandis_hbai_adult, and usehousehold_count_peopleas the per-person divisor. Retrain the cached models.imputations/consumption.py) and WAS wealth (imputations/wealth.py): keep results with explicit age counts computed in uk-data (the LCF and WAS definitions differ; flag the gap) instead of the deprecatedis_child/is_adult/num_children/num_adults.imputations/capital_gains.py):adult_index(now explicitly "rank among household members aged 18 or over") is unchanged; switch tois_household_headif the reference person is intended.🤖 Generated with Claude Code