Skip to main content

PAYE

Implementation of UK Income Tax Pay-As-You-Earn algorithms

In the UK, many employees and pensioners pay income tax in weekly or monthly installments as a deduction on their payslip under a system known as Pay-As-You-Earn or PAYE.

In this system, His/Her Majesty's Revenue and Customs (HMRC) gives the employer/pension provider a "Tax Code" which they use to calculate how much income tax to deduct.

This package implements the algorithms for calculating the income tax due as defined by HMRC in their "SPECIFICATION FOR PAYE TAX TABLE ROUTINES" from version 18, dated March 2020 onwards. This is what is meant by "the specification" in the rest of this document.

HMRC Constants

The algorithms use a set of constants that are dependent on tax year and are defined in the specification.

This package reads the constants from a TOML file 'hmrc.toml' which needs to be updated for each new tax year.

Exported Objects

  1. the TaxCode class
  2. the Payslip class

Usage

Weekly vs Monthly pay is selected by the environment variable PAYE_PERIOD: PAYE_PERIOD=weekly or PAYE_PERIOD=monthly

if unset, monthly is assumed

The inputs are:

  1. The pay date
  2. Your basic pay for the week / month
  3. Your tax code for the week / month (as given by HMRC via a letter or your Personal Tax Account on gov.uk)
  4. Any pay adjustments for the week / month (e.g. bonus)
  5. Any payrolled benefits in kind ... and for cumulative tax codes;
  6. Your total gross pay for the tax year including this week / month
  7. The income tax you've paid so far this tax year, NOT including this week/month

Use these to create an instance of the Payslip class

The income tax for this week / month is provided by the income tax property of the payslip.

For example:

import paye
from decimal import Decimal
from fiscalyear import FiscalDate

payslip = paye.Payslip(
  pay_date = FiscalDate(2026, 4, 30),
  basic_pay=Decimal('1156.25'),
  code=paye.TaxCode('1257L'),
  pay_to_date=Decimal('1156.25'),
  tax_to_date_non_inclusive=Decimal('0.00')
)
print(f"Income tax due this period = {payslip.income_tax}")

Note on weekly pay

The algorithms in the specification use 52 periods for weekly pay, but 52 * 7 = 364 so 5th of April (or 4th and 5th on a leap year) have week number 53. The HMRC test cases do not validate the algorithm for week 53 so this package may calculate incorrect income tax for weekly paid employees if the pay day falls in week 53.

Testing

This module is validated against the test cases provided by HMRC

Metadata

Release files for paye 0.10.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for paye 0.10.0
File Size Uploaded
paye-0.10.0.tar.gz 94.2 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for paye 0.10.0
File Interpreter ABI Platform
paye-0.10.0-py3-none-any.whl Python 3 none any Details

Total release size: 104.4 kB

Release files / paye-0.10.0.tar.gz

Download URL paye-0.10.0.tar.gz
Size 94.2 kB
Tags Source
SHA-256 checksum
How to use checksums
58df84ac4d21aabb0519a7e39e7fcb0e7b88d82ad5c08b826d9e722d8ddfb45f
BLAKE2b-256 checksum
How to use checksums
e9a3e900fffb4f9cbd83149f5cf605abe108290dde50a150e4b57a1670b91fea
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via Hatch/1.17.0 {"ci":null,"cpu":"x86_64","distro":{"libc":{"lib":"glibc","version":"2.43"},"name":"Arch Linux"},"implementation":{"name":"CPython","version":"3.14.6"},"installer":{"name":"hatch","version":"1.17.0"},"openssl_version":"OpenSSL 3.6.3 9 Jun 2026","python":"3.14.6","system":{"name":"Linux","release":"7.1.4-arch1-1"}} HTTPX2/2.3.0

Release files / paye-0.10.0-py3-none-any.whl

Download URL paye-0.10.0-py3-none-any.whl
Size 10.2 kB
Tags Python 3
SHA-256 checksum
How to use checksums
ab2ac4e640eebb9c0ee7d4b34a35f9cb6d6600530e31f72dbf5ada10d504e4b8
BLAKE2b-256 checksum
How to use checksums
241913ec9eac6498f20779c9d75d2c50e67951d2f391cc5a5ed02ab387f0f899
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via Hatch/1.17.0 {"ci":null,"cpu":"x86_64","distro":{"libc":{"lib":"glibc","version":"2.43"},"name":"Arch Linux"},"implementation":{"name":"CPython","version":"3.14.6"},"installer":{"name":"hatch","version":"1.17.0"},"openssl_version":"OpenSSL 3.6.3 9 Jun 2026","python":"3.14.6","system":{"name":"Linux","release":"7.1.4-arch1-1"}} HTTPX2/2.3.0

Release history Release notifications | RSS feed

This release

0.10.0 This release

2 release files

0.9.0

2 release files

0.8.1

2 release files

0.8.0

2 release files

0.6.2

2 release files

0.6.0

2 release files

0.5.0

2 release files

0.4.2

2 release files

0.4.1

2 release files

0.4.0

2 release files

0.1.6

2 release files

0.1.5

2 release files

0.1.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page