Functional Weave
Code in Rust

payroll.income-tax@1.0.0

README.md

4,386 bytes · view raw

# payroll.income-tax

Status: needs review by a qualified payroll professional before it is published.

PAYE income tax for one payment. Give it the employee's tax code, the pay
frequency and tax period (from `payroll.tax-period`), this period's taxable pay,
the taxable pay and tax so far this tax year, and the pay date; it returns the
tax to deduct (or refund) and the running totals.

## Which method

This follows HMRC's **"Specification for PAYE tax table routines"** (version
24.0, February 2026), the computerised form of the printed tax tables that
payroll software is expected to implement. It is not a "divide the annual
bands by 12" approximation, and the difference shows up in pence:

- **Free pay** for a code is worked out per week or month from
  `number x £10 + £9`, rounded *up* to the penny, with codes over 500 split into
  blocks of 500 (£96.16 a week, £416.67 a month each) plus a remainder, exactly
  as paragraph 4.3.1 says. 1257L is £241.92 a week and £1,048.26 a month.
- **Taxable pay** is rounded *down* to the whole pound.
- The **band thresholds to date** are `annual band x n / 52` (or `/ 12`) held
  to four decimal places without rounding; the test of which band applies uses
  that figure rounded *up* to the pound, the tax formula uses it exactly.
- Every tax formula is worked to four decimal places and the result is
  rounded *down* to the penny.

All of that is done in integer ten-thousandths of a pound, so the three
languages agree to the penny. HMRC notes (paragraph 16) that the printed
tables can differ from this specification by 1p, exceptionally 2p; this
capability matches the specification, not the printed tables.

## What it handles

- Cumulative codes: tax due to date on pay to date, less tax already deducted.
  A negative result is a refund.
- Week 1 / month 1 codes (`W1`, `M1`, `X`): each payment on its own, with the
  week 1 figures (week 2 for fortnightly, week 4 for four-weekly pay). The
  year-to-date arguments are only added to for the running totals.
- Weeks 53, 54 and 56 are always non-cumulative (paragraph 14).
- Suffix codes, K codes, 0T, BR, D codes (`D0` 40%, `D1` 45%; Scotland `SD0`
  21% to `SD3` 48%, `SD2` 47% in 2023-24) and NT. NT on a cumulative basis
  refunds all tax deducted so far this year.
- Scottish (S), Welsh (C) and rest-of-UK bands for 2023-24 to 2026-27. Welsh
  rates are held as their own rows even though they currently equal the
  rest-of-UK rates, because the Senedd can set them separately.
- **The overriding limit** (the "K-code 50% rule"): tax deducted from a payment
  may not exceed 50% of that payment. Under a cumulative code the tax held
  back is recovered in later periods automatically, because the next
  calculation compares tax due to date with tax actually deducted
  (`taxNotDeducted` reports what was held back). The limit never restricts a
  refund, and on negative pay it is zero (paragraph 4.5.4).

## What it does not do

- Payrolled benefits in kind: the limit is applied to the whole of `pay`; if
  you payroll benefits, the limit should be applied to cash pay only.
- Mid-year changes of region: supply the code in force for this payment; the
  pay and tax to date carry over, as the specification says.
- It trusts `previousTaxToDate` to be tax actually deducted, as HMRC's
  routine requires.
- The newest band rows have no end date. They stay in force until a new
  version adds the next tax year, so a 2027-28 pay date is answered with
  2026-27 bands until then.

## Sources

- HMRC, "Specification for PAYE tax table routines", version 24.0 (February
  2026), paragraphs 3-16 and Appendices A-C (band widths, rates, Maxrate 50%):
  https://www.gov.uk/government/publications/payroll-technical-specifications-income-tax
- HMRC, "Rates and thresholds for employers" for each year (rest-of-UK,
  Scottish and Welsh bands and the 1257L emergency code):
  https://www.gov.uk/guidance/rates-and-thresholds-for-employers-2023-to-2024,
  https://www.gov.uk/guidance/rates-and-thresholds-for-employers-2024-to-2025,
  https://www.gov.uk/guidance/rates-and-thresholds-for-employers-2025-to-2026,
  https://www.gov.uk/guidance/rates-and-thresholds-for-employers-2026-to-2027
- The Income Tax (Pay As You Earn) Regulations 2003 (SI 2003/2682), regulation
  23 (cumulative basis, overriding limit):
  https://www.legislation.gov.uk/uksi/2003/2682/regulation/23