Skip to content

State how PolicyEngine-US taxes estate_income in the export-mass notes - #1109

Open
MaxGhenis wants to merge 1 commit into
mainfrom
fix/estate-income-agi-note
Open

MaxGhenis wants to merge 1 commit into
mainfrom
fix/estate-income-agi-note

Conversation

@MaxGhenis

Copy link
Copy Markdown
Contributor

PolicyEngine/policyengine-us#9633 (released in policyengine-us 2.23.2, 2026-10-03) put estate and trust income into federal gross income and the NIIT base. That made a Microcosm calibration note stale. Checking it against the engine Microcosm actually pins showed the note was already wrong before #9633.

What changes

Two comments, no code paths:

  • tools/build_us_fiscal_refresh_release.py, the estate_income entry in US_EXPORT_INPUT_MASS_REVIEWED_EXCLUSIONS. The last sentence said "estate_income does not feed AGI in PolicyEngine-US (loss-cap input only), so pinning it identifies the export dimension without moving revenue." It now states the mechanism for both engine versions and says the exclusion rests on the band math, not on revenue neutrality.
  • packages/microcosm-build/src/microcosm/build/us_runtime/fiscal_targets.py, the Build H comment above the SOI Table 1.4 estate and other-income mappings. It said estate_income and miscellaneous_income "do not currently add to AGI (loss-cap / catch-all only)". It now says both move federal income tax and how.

What the engine does

Read from the installed packages and checked by running households (single filer, Texas, 2024, $100,000 of wages):

policyengine-us 2.2.1 (the uv.lock pin) from 2.23.2 (#9633)
estate_income in gross income / AGI no positive part, non-dependents
estate_income losses deducted above the line by loss_ald (§ 461(l)) same
QBI deduction counts while estate_income_would_be_qualified (default true) same
NIIT base no estate_net_investment_income (estate_income + K-1 box 14 code H input, non-dependents)
miscellaneous_income in gross income yes yes

On 2.2.1, −$50,000 of estate income lowers AGI from $100,000 to $50,000, and +$100,000 leaves AGI unchanged but adds a $17,080 QBI deduction, cutting income tax from $13,841 to $10,083.40. So "loss-cap input only" and "without moving revenue" were false at the pin, and already false when the sentence was written (Microcosm then pinned 1.764.6, which already had both paths). miscellaneous_income has been a gross-income source since 2023.

The exclusion stays

Its separate argument doesn't depend on AGI, and I re-checked the numbers on main:

  • The export-mass gate takes its reference from --export-input-mass-reference-h5, which has no default. The committed launchers require the c2065b64 file, and the newest fiscal-refresh release (populace-us-2024-0fb05b6-4b57d15a287c-20260930T150401Z) records that reference.
  • That file carries $98.434B of net estate_income (+$103.973B, −$5.539B), so the ±50% band is [$49.217B, $147.651B].
  • The SOI Table 1.4 net target is ~$46.74B for 2024 ((47.892 − 4.899) × 1.0872). It sits below the floor, so a correctly calibrated column cannot pass.
  • If an operator ever passes the current default instead (populace-us-2024-spm-20260915, net $46.753B), the band becomes [$23.377B, $70.130B] and contains the target. The exclusion would then need re-adjudicating.

Next release build

Once Microcosm's policyengine-us pin reaches 2.23.2, the next release build re-weights against the new AGI definition. Estate and trust income then counts in AGI, so the targets fiscal_targets.py maps to the engine's adjusted_gross_income and income_tax (SOI and CBO AGI and income-tax lines) see different model values for the same weights. Microcosm's pin is still 2.2.1 as of this PR; this PR doesn't change it.

Search for other stale claims

I swept every mention of estate income in the repo (about 40 files: code, specs, docs, tests, experiments and the root journals). These two comments were the only statements about how PolicyEngine-US taxes estate income that were wrong. The root PROGRESS_*.md journals mention estate_income only as a calibration target, which is history and is left alone. Two other comments near the target are stale, but about Microcosm's own exclusion register rather than estate income (the "two SOI-identified columns" comment near the post-export gate, and miscellaneous_income listed as "deliberately NOT excluded"). They're tracked in #1108, not changed here.

Tests

  • ruff check and ruff format --check pass on both files.
  • The engine-free test files that load the builder or fiscal_targets (27 files): see the comment below once the local run finishes; CI runs them too.
  • Neither file is in a committed spec or source pin: code_identity hashes package sources into build manifests at build time, and the serializer registry names a write function, not a digest.

🤖 Generated with Claude Code

The estate_income reviewed exclusion said estate_income "does not feed AGI
in PolicyEngine-US (loss-cap input only), so pinning it identifies the export
dimension without moving revenue", and the fiscal_targets comment said
estate_income and miscellaneous_income "do not currently add to AGI".

Both were false even for the pinned engine (policyengine-us 2.2.1): loss_ald
deducts estate_income's negative part above the line under section 461(l),
estate_income counts toward qualified business income, and
miscellaneous_income is a gross-income source. From policyengine-us 2.23.2
(PolicyEngine/policyengine-us#9633) a non-dependent's positive estate_income
is also gross income and AGI and enters net investment income.

The exclusion itself stays: the reference h5 the gate is run against
(c2065b64) still carries $98.434B, so the +/-50% band's floor ($49.217B) sits
above the SOI net target (~$46.74B).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant