PolicyEngine / policyengine-us

The PolicyEngine US Python package contains a rules engine of the US tax-benefit system, and microdata generation for microsimulation analysis.
https://policyengine.org/us
GNU Affero General Public License v3.0
103 stars 176 forks source link

Recent problem with US itemized deduction calculations #1465

Closed martinholmer closed 1 year ago

martinholmer commented 2 years ago

Since the switch from OpenFisca-Core to PolicyEngine-Core, the US income tax calculations for those with itemized expenses have changed from what they were before the switch, and are now different from what TAXSIM35 produces. Below is a simple test case that illustrates the problem. After presenting the YAML test file and the test results, I show the TAXSIM35 results for this case.

Here is the YAML test file:

- name: Simple case that itemizes deductions on federal return
  absolute_error_margin: 0.01
  period: 2021
  input:
    people:
      person1:
        is_tax_unit_head: 1
        is_tax_unit_spouse: 0
        is_tax_unit_dependent: 0
        age: 40
        employment_income: 200_000
        real_estate_taxes: 12_000
        interest_expense: 24_000
        ssi: 0
        state_supplement: 0
        wic: 0
    spm_units:
      spm_unit:
        members: [person1]
        snap: 0
        tanf: 0
    tax_units:
      tax_unit:
        members: [person1]
        premium_tax_credit: 0
    households:
      household:
        members: [person1]
        state_code: TX
  output:
    taxsim_tfica: 11_753.60
    income_tax: 33_947.00

Here are the test results, which show a $3200 difference in US income tax liability:

================================= FAILURES ===================================
_______________________________ test session _________________________________
/Users/mrh/work/PolicyEngine-US/US/q21-id0.test.yaml:
  Test 'Simple case that itemizes deductions on federal return':
    income_tax@2021: [37147.] differs from 33947.0
                     with an absolute margin [3200.] > 0.01
========================= short test summary info ============================
FAILED q21-id0.test.yaml::
============================ 1 failed in 1.56s ===============================

Notice that the $3200 difference is equal to the product of the tax unit's MTR (32%) and the tax unit's allowable real estate tax deduction ($10,000). The test trace output shows the the value of the tax_liability_if_itemizing variable is computed correctly at $33,947, but the income tax variable does not reflect that value for some reason (even though the tax_unit_itemizes variable is true).

And here are the TAXSIM35 results for this test case:

 NBER TAXSIM Model v35 (10/24/22) With TCJA
 State law coded through        2021
 Later state laws extrapolated from that year.
 Marginal tax rate wrt taxpayer earnings.

 Input Data:                   
      1. Record ID:                       1.
      2. Tax Year:                 2021.00
      3. State Code:                  0.00
      4. Marital Status:              1.00 Single  
    5-6. Age (Txpyr/Spouse):         40.00       0.00
      7. Dependent Exemptions:        0.00
   8-10. #deps for CCC/CTC/EIC:       0.00       0.00       0.00
  11-12. Wages (Txpyr/Spouse):   200000.00       0.00
 11a12a Self-employment income:       0.00       0.00
     13. Dividend Income:             0.00
     14. Interest Received:           0.00
     15. Short Term Gains:            0.00
     16. Long Term Gains:             0.00
     17. Other Property:              0.00
     18. Other Non-Property:          0.00
     19. Taxable Pensions:            0.00
     20. Gross Social Security:       0.00
     21. Tot/Txpy/Spouse UI   :       0.00       0.00       0.00
     22. Non-taxable Transfers:       0.00
     23. Rent Paid:                   0.00
     24. Property Taxes Paid:     12000.00
     25. Other Itemized Deds:         0.00
     26. Child Care Expenses:         0.00
     27. Mortgage Interest:       24000.00
     28. S-Corp profits:              0.00
  29 31. Txpy/Spous QBI w/o PO:       0.00       0.00
  30 32. Txpy/Spouse SSTB w PO:       0.00       0.00

 Basic Output:               
      1. Record ID:                1.                            
      2. Year:                           2021
      3. State (SOI code):                  0                            
      4. Federal IIT Liability:      33947.00
      5. State IIT Liability:            0.00
      6. SS Payroll Tax Liability:   23507.20
 Marginal Rates wrt  Earner
      7. Federal Marginal Rate:         32.00
      8. State Marginal Rate:            0.00
      9. Taxpayer SS Rate:               2.90

 Federal Tax Calculation:              Base        + $1
     10. Federal AGI                200000.00   200001.00
     11. UI in AGI 1979+                 0.00        0.00
     12. Social Security in AGI 84       0.00        0.00
     13. Zero Bracket Amount             0.00        0.00
     14. Personal Exemptions             0.00        0.00
     15. Exemption Phaseout 1991+        0.00        0.00
     16. Deduction Phaseout 1991+        0.00        0.00
     17. Deductions allowed          34000.00    34000.00
         QBI deduction                   0.00        0.00
     18. Federal Taxable Income     166000.00   166001.00
     19. Federal Regular Tax         33947.00    33947.32
     20. Exemption Surtax 1988-96        0.00        0.00
     21. General Tax Credit 1975-8       0.00        0.00
     22. Child Tax Credit*17/22 98       0.00        0.00
     23  Refundable Part                 0.00        0.00
     24. Child Care Credit 1076+         0.00        0.00
     25. Earned Income Credit 1975       0.00        0.00
     26. Alternative Min Income:    176000.00   176001.00
     27. AMT                             0.00        0.00
     28. Income Tax Before Credits   33947.00    33947.32
     29. FICA                        23507.20    23507.24
         Taxpayer share of FICA      11753.60    11753.62
nikhilwoodruff commented 2 years ago

Thanks @martinholmer for narrowing down this issue, which also confused me a bit. For some context, the cause is a new feature/improvement we added: the computation tree now shows the branch of the simulation (the itemized/non-itemized loops are included as their own subtrees to aid debugging). But it looks like there's some leakage, because when I look at the computation tree, I see three places SALT is calculated (in order):

  1. SALT deduction assuming itemization (works fine, = $10,000)
  2. SALT deduction assuming no itemization (works fine, = $0)
  3. SALT deduction assuming optimal itemization (seems to be erroneously $0, which makes me think the neutralization applied in (2) is remaining 'sticky').

I'll give it a proper go at a fix on Monday.

martinholmer commented 1 year ago

Merging pull request #1523 fixed the bug reported in issue #1465.

@nikhilwoodruff, Thanks for getting the itemized deduction logic working again!