Your bank export becomes a Form 990-EZ draft your board can review.

Upload the year's transactions. Every Part I line with activity is filled, explained, and tied to the IRS instruction that put it there. Rows a person should check are flagged.

Page one of the drafted Form 990-EZ, filled from a bank export and stamped DRAFT, NOT A FILING
Line 1, contributions
Line 6d, fundraising events
Line 9, total revenue

What you get.

The real IRS form, filled in and marked DRAFT on every page, and under it every Part I line with the transactions behind it. Open a line to see them and the IRS instruction each one follows.

Line
Revenue, expenses, and changes in net assets
Amount
How it was decided

How it works.

Three readers and a calculator. The readers sort. The calculator adds. The readers never add.

1

Upload the year's transactions

A CSV from your bank with a date, a description, and an amount on each row. No categories needed.

2

Two readers sort every row

The Preparer and the Reviewer each put every transaction on a Part I line, working separately, and each quotes the IRS instruction that supports the choice.

3

A Referee settles disagreements

When the two readers differ, the Referee reads both instructions and decides. You see all three opinions. Nothing is settled silently.

4

You review and download

Python adds the totals and checks every quoted instruction, the Referee's included, against the IRS text. Flagged rows wait for you. Then download the PDF, marked DRAFT.

When the readers disagree.

Is the math right?

LineReturns checkedMatched the filerRate

About 203,699 of these returns reached the IRS in 2024. A late one costs $25 a day, capped at the lesser of $13,000 or 5% of gross receipts, and three missed years in a row revoke the exemption automatically. The IRS auto revocation file dated 8 September 2026 lists 1,065,726 rows with no reinstatement date. Of the returns in the IRS batch this project checks itself against, 30.0% had no paid preparer, so the organisation did the form itself.

What this is not.

Not a filing. The output is a draft. For tax year 2025 the IRS requires Form 990-EZ to be filed electronically, which needs an Authorized IRS e-File Provider. This project is not one.
Not signed. An officer of the organisation must review and sign. The Paid Preparer block is left blank on purpose.
Not the whole form. Only Part I is drafted. Parts II through VI and all Schedules are out of scope. The app does not pretend to fill them.
Not a verdict. Classification is a model judgement. The two-reader design surfaces uncertainty; it does not eliminate it. Low-confidence and disputed rows are flagged for a human.
Not tested on your books. The demo ledger is made up. The accuracy numbers above come from real IRS filings, never from that file.

Get started.

Runs in the browser. Or on your own computer with a free Google Gemini key.

Your transactions are sent to Google's Gemini API to be sorted, and the blank IRS form is fetched once from irs.gov. On the hosted app the CSV is uploaded to Streamlit Cloud and read from a temporary directory that is deleted when the run ends. Run it on your own computer and the file never leaves it.

git clone https://github.com/ishal1410/ninetyninety
cd ninetyninety
pip install -r requirements.txt
cp .env.example .env    # free key: aistudio.google.com/apikey
streamlit run app.py