diff --git a/changelog.d/746.md b/changelog.d/746.md new file mode 100644 index 000000000..1d14c4190 --- /dev/null +++ b/changelog.d/746.md @@ -0,0 +1 @@ +- Expand the National Insurance documentation page with a per-class computation section, add Class 3 (voluntary) to the modelling table, link the underlying variables, and add a references section; also fix the boolean-chain warning in the rates chart. diff --git a/docs/book/programs/gov/hmrc/national-insurance.ipynb b/docs/book/programs/gov/hmrc/national-insurance.ipynb index 8bdb55af3..71841820c 100644 --- a/docs/book/programs/gov/hmrc/national-insurance.ipynb +++ b/docs/book/programs/gov/hmrc/national-insurance.ipynb @@ -133,30 +133,33 @@ "source": [ "# @title\n", "import pandas as pd\n", - "from tabulate import tabulate\n", "\n", "\n", "data = {\n", - " \"Class\": [\"Class 1\", \"Class 2\", \"Class 4\"],\n", + " \"Class\": [\"Class 1\", \"Class 2\", \"Class 3\", \"Class 4\"],\n", " \"Methodology & Basis\": [\n", " \"Based on employment income. \\n- Monthly and annual calculations.\",\n", " \"Based on self-employment income. \\n- Weekly flat rate.\",\n", + " \"Voluntary contributions for those filling gaps in their NI record. \\n- Weekly flat rate.\",\n", " \"Derived from self-employment income minus Class 1 employee NI.\",\n", " ],\n", " \"Thresholds & Limits\": [\n", " \"Primary Threshold, Upper Earnings Limit\",\n", " \"Small Profits Threshold\",\n", + " \"None (voluntary)\",\n", " \"Lower Profits Limit, Upper Profits Limit\",\n", " ],\n", " \"Rate Application\": [\n", " \"Main and Additional rates\",\n", " \"Flat rate\",\n", + " \"Flat rate\",\n", " \"Main and Additional rates\",\n", " ],\n", " \"Reference\": [\n", " \"Social Security Contributions and Benefits Act 1992 s. 8\",\n", - " \"Social Security and Benefits Act 1992 s. 11\",\n", - " \"Social Security and Benefits Act 1992 s. 15\",\n", + " \"Social Security Contributions and Benefits Act 1992 s. 11\",\n", + " \"Social Security Contributions and Benefits Act 1992 s. 13\",\n", + " \"Social Security Contributions and Benefits Act 1992 s. 15\",\n", " ],\n", "}\n", "\n", @@ -164,6 +167,11 @@ "df" ] }, + { + "cell_type": "markdown", + "metadata": {}, + "source": "## How PolicyEngine computes National Insurance liability\n\nFor each person, PolicyEngine computes NI contributions class-by-class:\n\n- **Class 1 employee** (`ni_class_1_employee`): the sum of `ni_class_1_employee_primary` (main rate on earnings between the Primary Threshold and the Upper Earnings Limit) and `ni_class_1_employee_additional` (additional rate on earnings above the UEL).\n- **Class 1 employer** (`ni_class_1_employer`): paid on earnings above the Secondary Threshold; surfaced through the `ni_employer` variable.\n- **Class 2** (`ni_class_2`): a flat weekly rate paid by the self-employed with profits above the Small Profits Threshold.\n- **Class 3** (`ni_class_3`): a voluntary flat weekly rate; the variable is exposed but defaults to zero unless explicitly set.\n- **Class 4** (`ni_class_4`): main rate between the Lower and Upper Profits Limits plus additional rate above the UPL, capped at the published Class 4 maximum.\n\nThe individual total `national_insurance` sums the four employee and self-employed components directly — `ni_class_1_employee + ni_class_2 + ni_class_3 + ni_class_4` — so voluntary Class 3 contributions are included in the household-side liability. The convenience aggregates `ni_employee` (Class 1 employee only) and `ni_self_employed` (Class 2 + Class 4) are also exposed for reporting. The Class 1 *employer* charge (`ni_class_1_employer`, surfaced as `ni_employer`) is an employer-side cost rather than part of the individual's `national_insurance`, so it is tracked separately and feeds the government revenue aggregates on its own.\n\nParameters live in `policyengine_uk/parameters/gov/hmrc/national_insurance/` and the per-class formulas in `policyengine_uk/variables/gov/hmrc/national_insurance/`." + }, { "cell_type": "markdown", "metadata": { @@ -1529,16 +1537,6 @@ ] }, "outputs": [ - { - "name": "stderr", - "output_type": "stream", - "text": [ - "/var/folders/8f/pgfhysmd5ls3jnxb_5j7yy340000gn/T/ipykernel_41381/4247299465.py:2: UserWarning:\n", - "\n", - "Boolean Series key will be reindexed to match DataFrame index.\n", - "\n" - ] - }, { "data": { "application/vnd.plotly.v1+json": { @@ -2688,7 +2686,7 @@ ], "source": [ "fig = px.line(\n", - " df[df[\"Threshold\"] == False][df.Value < 1], # Don't plot the flat rate,\n", + " df[(df[\"Threshold\"] == False) & (df[\"Value\"] < 1)], # Don't plot the flat rate,\n", " x=\"Instant\",\n", " y=\"Value\",\n", " color=\"Label\",\n", @@ -2714,6 +2712,17 @@ "fig = format_fig(fig)\n", "fig" ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "## References\n", + "\n", + "- [Social Security Contributions and Benefits Act 1992](https://www.legislation.gov.uk/ukpga/1992/4/contents) — primary statute defining each NI class.\n", + "- HMRC, [Rates and allowances: National Insurance contributions](https://www.gov.uk/government/publications/rates-and-allowances-national-insurance-contributions).\n", + "- HMRC, [National Insurance contributions outturn statistics](https://www.gov.uk/government/collections/income-tax-statistics-and-distributions)." + ] } ], "metadata": { @@ -2739,4 +2748,4 @@ }, "nbformat": 4, "nbformat_minor": 0 -} +} \ No newline at end of file