A secure, local-first application for tracking charitable donations, designed as a modern replacement for Intuit's discontinued "ItsDeductible" service.
This application was "vibe-coded" into existence as a personal response to the retirement of ItsDeductible. It aims to provide the same ease of use for tracking non-cash, cash, and asset donations while adhering to modern security standards and keeping your financial data exactly where it belongs: on your own machine.
We have compiled a comprehensive, multi-part User Guide to help you set up and get the most out of Donation Tracker:
- Getting Started: Platform installation, database and receipt photo storage locations, tax profile setup, and understanding OBBBA regulatory calculations (0.5% AGI Floor, benefit caps, and ceilings).
- Using Donation Tracker: Navigating the dashboard states, recording physical items (catalog search & custom items), cash, stock donations, and managing history.
- Reports & Sync: Generating annual tax reports (Form 8283 prep), print-friendly pages, CSV flat exports, and multi-machine sync procedures.
- Item Catalog: A searchable directory of over 1,700 items with Fair Market Values (FMV) pre-seeded from industry-standard data. Easily add and save your own custom items if they aren't in the default catalog.
- Donation Ledger: Track physical items, cash contributions, and asset transfers (stocks/securities) in one central place.
- Organization Management: Maintain a directory of your favorite charities, including Tax IDs and addresses.
- Receipt & Photo Attachments: Securely attach local images and receipts to your donation events. Photos are copied to a private local storage directory, with automatic cleanup of image files when events are deleted to prevent storage leaks.
- Interactive Dashboard: View annual summaries of your giving, broken down by type and organization.
- OBBBA-Compliant Tax Savings Engine (2026+): Estimate tax savings dynamically based on AGI and One Big Beautiful Bill Act compliance rules.
- AGI-Based Deduction Floor & Ceilings: Automatically track progress against a statutory AGI floor (0.5% of AGI) before deductions kick in, and enforce cascading contribution ceilings (30% for assets/stocks, 50% for physical items, and 60% for cash) with carryover notifications.
- Visual Progress Indicators: View interactive progress bars on the dashboard indicating how close you are to clearing your deduction floor and maximizing statutory ceilings.
- Data Import & Export (Sync Packages): Export your entire database (seeded/custom catalog items, charities, events, and receipts) to a compressed
.dtpackfile, and seamlessly import/merge data from other devices with automatic duplicate detection and database safety rollbacks. - Annual Tax Reporting: Generate IRS-compliant annual summaries grouped by organization and date. Includes print-optimized layouts and CSV export for data portability.
- Frontend: Next.js (App Router)
- Desktop Wrapper: Electron (Bundled Server Pattern)
- Database: SQLite via Prisma ORM
- Styling: Tailwind CSS
- Runtime: Node.js
Donation Tracker is designed around a single-user, offline-first architectural model. Please review our security guarantees and threat model to understand how your data is protected:
- Access Control: Access to the application user interface is protected by a master password check. Multiple user accounts or remote roles are not supported.
- Credential Storage: The application password is never stored in plaintext on the local disk. It is securely hashed using the memory-hard
scryptkey derivation function with a unique, cryptographically secure salt. - Local-First & Offline: All donation ledger data and uploaded receipt photos reside on your local disk. The application does not upload or sync any sensitive financial data to the cloud.
- No At-Rest Encryption: The SQLite database (
production.db) and uploaded receipt image files are stored in plaintext on the local storage directory and are not encrypted at rest by the application. - Threat Actor Exclusions: The application's threat model assumes a secure local host environment. It does not protect against a malicious local actor who has physical or administrator-level access to the host machine's disk. If storage-level encryption is required, users are encouraged to use native OS disk encryption tools (e.g., FileVault on macOS, BitLocker on Windows, or dm-crypt on Linux).
The item database is seeded using data historically provided by Intuit's ItsDeductible service, ensuring that Fair Market Value estimates for clothing, household goods, and other items are consistent with common tax preparation standards.
- Node.js (LTS version recommended)
- npm or yarn
- macOS, Windows, or Linux (cross-platform building is fully supported)
-
Clone the repository.
-
Install dependencies:
npm install
-
Initialize the development database and seed the catalog:
npx prisma migrate dev --name init npx prisma db seed
[!NOTE] How Database Environments Work:
dev.db(stored inprisma/dev.db) is the local sandbox database for development and testing. The default path is set in.env(which is tracked by Git) so that Prisma CLI commands (migrate,seed, etc.) work out of the box.production.dbis the database used when running the packaged application (Electron desktop or Docker). This separation ensures developer activity never alters your real tax data.
-
Set Access Password: Start the development server (see below). On your first launch in the browser, you will be automatically prompted by a setup wizard to configure your local access password.
The Setup Wizard automatically generates a secure
AUTH_SECRETand writes it along with your chosenAPP_PASSWORD(securely hashed usingscrypt) to a.env.localfile in your root folder (which is ignored by Git).Tip: If you want to bypass the wizard or pre-configure these manually, you can copy the
.env.samplefile to.env.localand define them there before running. If you specify your password in plaintext, the application will automatically hash it and overwrite.env.localon first boot for enhanced security.
Start the development server:
npm run devOpen http://localhost:3000 in your browser.
Start the app in a desktop window:
npm run desktop:devFor self-hosting or running in a headless environment, you can run the application as a Docker container. See π³ Running with Docker below for details.
To create a packaged desktop application for your platform:
- Prerequisites: Install
gettextvia Homebrew for DMG packaging:brew install gettext
- Build:
npm run desktop:build
- Build:
npm run desktop:build
- Build:
npm run desktop:build
The output will be generated in the dist/ directory.
When running the packaged desktop application, environment variables from .env.local are not loaded. The app uses an automated configuration system where the database (production.db) and configuration (config.json) are stored in the platform's standard user data directory:
- macOS:
~/Library/Application Support/Donation Tracker - Windows:
%APPDATA%\Donation Tracker(e.g.,C:\Users\<username>\AppData\Roaming\Donation Tracker) - Linux:
~/.config/Donation Tracker
An AUTH_SECRET is automatically generated if missing, and a Setup Wizard will guide you to configure your APP_PASSWORD on first launch (saving it as a secure scrypt hash in config.json).
Alternatively, if you prefer to bypass the setup GUI, you can set your password for the first time by launching the app once from the terminal with the APP_PASSWORD environment variable. This will automatically hash the password and persist the hash in config.json for all subsequent GUI launches:
- macOS:
APP_PASSWORD=your_password /Applications/Donation\ Tracker.app/Contents/MacOS/Donation\ Tracker
- Windows (PowerShell):
$env:APP_PASSWORD="your_password"; & "$env:USERPROFILE\AppData\Local\Programs\donation-tracker\Donation Tracker.exe"
- Linux:
APP_PASSWORD=your_password donation-tracker
As an alternative to running the Electron packaged desktop application, you can build and run a lightweight, standalone, platform-independent Docker container. This is ideal for self-hosting on a home server, NAS, or local machine.
- Docker installed on your host system.
To run the application using Docker Compose:
-
Start the service: Run the following command from the root of the repository to start the container in the background:
docker compose up -d
This will pull the latest pre-built container image and launch the service.
-
Configure (Optional): Open the
docker-compose.ymlfile to configure:APP_PASSWORD: The master password used to log in. Changeyour_secure_passwordto your own password.NEXTAUTH_URL: Set tohttp://localhost:3000by default. For network access from other machines, changelocalhostto the host's local IP address (e.g.http://192.168.1.100:3000).volumes: Mounts./local-datain the host directory to/app/datainside the container, preserving your database and uploads.
-
Manage the container:
- Stop:
docker compose down - Logs:
docker compose logs -f
- Stop:
Multi-architecture container images (supporting both linux/amd64 and linux/arm64 / Apple Silicon) are automatically built and published to GitHub Container Registry (GHCR).
-
Pull the latest image:
docker pull ghcr.io/padolph/donation-tracker:latest
-
Run the container: Make sure to pass a secure password via the
APP_PASSWORDenvironment variable, and mount a persistent local directory to/app/datato store your SQLite database and uploaded receipts safely:docker run -d \ --name donation-tracker \ -p 3000:3000 \ -e APP_PASSWORD="your_secure_password" \ -e NEXTAUTH_URL="http://<YOUR_SERVER_IP>:3000" \ -v </path/to/local/storage>:/app/data \ ghcr.io/padolph/donation-tracker:main
APP_PASSWORD: The master password you will use to log into the application.NEXTAUTH_URL: (Required for Network Access) Replace<YOUR_SERVER_IP>with the local IP address of the machine running Docker (e.g.,192.168.1.100). NextAuth uses this to securely sign tokens and handle internal redirects. If you only intend to access the app on the same machine running Docker, you can usehttp://localhost:3000.-v(Volume Mount): Replace</path/to/local/storage>with the absolute path to a folder on your host machine where you want your SQLite database and uploaded attachments to live permanently.
Open http://<YOUR_SERVER_IP>:3000 in your browser.
If you want to build the container from source locally:
-
Build the image:
docker build -t donation-tracker . -
Run your local build:
docker run -d \ --name donation-tracker \ -p 3000:3000 \ -e APP_PASSWORD=your_secure_password \ -v $(pwd)/local-data:/app/data \ donation-tracker:latest
When the container starts up for the first time, it automatically creates and seeds the SQLite database (production.db) and creates the image upload directory (donations/) inside your mounted /app/data volume:
- SQLite Database path:
/app/data/production.db - Image uploads path:
/app/data/donations
The project uses Jest and React Testing Library for comprehensive test coverage.
npm testBuilt with β€οΈ as a secure, personal tool for better giving.