README.md
May 8, 2026 · View on GitHub
Your Personal Finance Command Center for Israeli Banking
Automatically aggregate, categorize, and analyze your finances from all Israeli banks and credit cards in one beautiful dashboard.
Self-hosted · Open source · Hebrew & English (RTL) · Local-only by design
Website • Features • Quick Start • Banks & Cards • AI Integration
Why Nudlers?
Managing finances across multiple Israeli banks and credit cards is a nightmare. Different apps, different formats, no unified view. Nudlers solves this.
| The Problem | The Nudlers Solution |
|---|---|
| Scattered data across 5+ apps | One unified dashboard |
| Manual transaction logging | Automatic daily sync |
| Forgotten subscriptions and silent price hikes | Insights inbox flags them automatically |
| No cross-bank insights | AI-powered analysis |
| Time wasted on categorization | Smart auto-categorization |
| Missed budget alerts | WhatsApp notifications |
✨ Features
📊 Unified Financial Dashboard
See all your money in one place. Nudlers aggregates transactions from every Israeli bank and credit card into a single, beautiful interface.
- Multi-View Analytics — Switch between Summary, Budget, Category, Recurring Payment, and Balance Projection views
- Balance Forecasting — Predict your future bank balance based on recurring payments and upcoming credit card charges
- Real-Time Sync — Background syncing keeps your data fresh automatically
- Custom Billing Cycles — Track spending by your credit card billing cycle, not just calendar months
- Installment Tracking — Monitor ongoing installments with remaining payments and amounts
🧠 Intelligent Auto-Categorization
Stop wasting time manually categorizing transactions. Nudlers learns your spending patterns.
3-Phase Smart Categorization:
- Rule-Based Matching — Custom regex patterns for merchants you define
- Historical Learning — Remembers how you categorized "Aroma Coffee" and applies it automatically
- Selective Enrichment — Only fetches additional data when needed, avoiding bot detection
95%+ of transactions are categorized automatically after initial setup
🔔 Insights — anomalies worth your attention
A dedicated "Insights" view (תובנות) surfaces things that would otherwise hide in the noise. Everything is computed locally, fingerprinted so re-runs don't double-flag, and re-evaluated automatically after each daily sync.
- Price hikes on subscriptions — "Apple Music: ₪19.90 → ₪29.90 after 8 stable months." Catches silent price increases that most apps miss because the new amount clusters separately from the historical pattern.
- New recurring charges — Surfaces forgotten free trials that quietly turned into monthly charges, on the second or third confirmation.
- Category spend spikes — Flags weeks where a category jumps statistically far above its trailing-12-week mean (μ + 2σ). Skips income/refund weeks; requires real history before it'll fire.
- Daily WhatsApp digest — High and medium-severity anomalies are folded into the top of the daily summary message, so you see them without opening the app.
- Inbox actions — Dismiss, mark "this is normal," or acknowledge — with optimistic updates and rollback on failure.
📱 Native WhatsApp Integration
Get your daily financial summary delivered right to WhatsApp — no Twilio, no third-party services.
- Daily Summaries — Wake up to yesterday's spending overview, with insight alerts at the top when something fired
- Restart Notification — Optional one-shot ping when the app comes back up and the vault is locked, so you know to go unlock it (great for catching unexpected NAS reboots or deploys)
- Resilient Send Path — Connection is verified before each send and reconnected automatically if the WhatsApp Web session drifted into a stale state
- Group Support — Share summaries with family or partners
- QR Code Setup — Connect in seconds, session persists across restarts
🤖 AI-Powered Insights
Ask questions about your finances in plain language. Bring your own AI provider — any OpenAI-compatible API works (OpenRouter, OpenAI, Groq, Together, Gemini, LMStudio, Ollama, etc.).
"What did I spend on groceries this month?"
"Compare my dining expenses to last month"
"Show me my top 10 expenses"
🔌 MCP Integration for AI Assistants
Connect Nudlers directly to Claude Desktop, Cursor, or Claude Code using the Model Context Protocol.
Quick Setup (localhost):
{
"mcpServers": {
"nudlers": {
"command": "npx",
"args": ["-y", "supergateway@latest", "--sse", "http://localhost:6969/api/mcp"]
}
}
}
For remote/hosted instances, replace localhost:6969 with your server URL (see MCP Setup for details).
Now your AI assistant can query your finances, search transactions, and add manual expenses.
💰 Smart Budget Management
Set budgets by category and track them in real-time.
- Visual Progress Bars — See budget consumption at a glance
- Burndown Charts — Daily spending vs. ideal pace visualization
- Historical Comparison — Compare this month to previous months
- Overspend Alerts — Get notified before you exceed limits
📈 Smart Balance Projection
Know your future balance before it happens. Nudlers projects your bank balance for the next 30 days.
- Predictive Analytics — Combines current balances, detected recurring bank transactions, and upcoming credit card settlements.
- Visual Trends — Interactive charts show your balance trajectory and highlight potential risks.
- Manual Overrides — Add manual recurring payments (like rent or direct debits) that the system hasn't detected yet.
- Billing Cycle Awareness — Intelligently accounts for Israeli credit card billing cycles and settlement dates.
- Negative Balance Alerts — Visual indicators catch when your projected balance might drop below zero.
🔒 Bank-Grade Security
Your credentials never leave your machine unencrypted.
- AES-256-GCM Encryption — Industry-standard encryption for all credentials
- Local Processing — No cloud service sees your bank passwords
- Secure by Design — Credentials decrypted only at scraping time
- Memory-Locked Vault — Mandatory security layer. Your master key exists only in RAM. Even if your server is compromised, credentials remain unreadable without your passphrase
- Passkey / Biometric Unlock — Use TouchID, FaceID, or a hardware security key to unlock the vault without typing your passphrase
- Native 2FA Flows — Built-in support for OneZero's two-factor authentication and Bank Hapoalim's OTP, no third-party extensions required
- Zero Telemetry — No analytics, no remote logs, no "anonymized usage data." If you don't see it in DevTools, it isn't happening
🌐 Hebrew & English, with proper RTL
Built for the Israeli banking ecosystem, with first-class support for both languages.
- Live language switch — Toggle between עברית and English from the menu; the entire UI flips direction without a reload
- Real RTL — Card corners, arrow direction, table alignment, financial number layout — all behave correctly in both directions, not bolt-on right-to-left
- Hebrew display fonts — Heebo for the UI, with English text rendering in Inter when the app is in English mode
🔒 Memory-Locked Credentials (Vault)
Nudlers uses a Memory-Locked Vault for all credential encryption. Your master encryption key is "wrapped" with a passphrase and stored in the database. When the application starts, it remains in a "locked" state until you provide the passphrase (or use a passkey) via the UI.
- Non-Persistent: The decrypted key exists only in the application's memory (RAM).
- Auto-Lock: If the app restarts or the server reboots, the vault automatically locks.
- Brute-Force Protected: Key derivation uses
scryptwith a custom salt.
How It Works
┌─────────────────────────────────────────────────────────────┐
│ First-Time Setup │
│ │
│ 1. User creates a passphrase (8+ chars) │
│ 2. Random 256-bit master key is generated │
│ 3. Master key is wrapped with passphrase (scrypt + AES) │
│ 4. Wrapped key stored in database │
│ 5. Master key held in memory → vault is unlocked │
│ 6. User optionally registers a passkey (biometric) │
└─────────────────────────────────────────────────────────────┘
┌─────────────────────────────────────────────────────────────┐
│ Subsequent Unlocks │
│ │
│ Option A: Passkey (default when registered) │
│ 1. Browser triggers WebAuthn challenge │
│ 2. User authenticates with biometric/security key │
│ 3. Server verifies, retrieves encrypted passphrase │
│ 4. Passphrase unwraps master key → vault unlocked │
│ │
│ Option B: Passphrase │
│ 1. User types passphrase │
│ 2. Passphrase derives wrapping key via scrypt │
│ 3. Wrapping key decrypts master key → vault unlocked │
└─────────────────────────────────────────────────────────────┘
┌─────────────────────────────────────────────────────────────┐
│ Legacy Migration │
│ │
│ If upgrading from env-var encryption: │
│ 1. UI detects NUDLERS_ENCRYPTION_KEY in environment │
│ 2. Prompts user to create a vault passphrase │
│ 3. All credentials re-encrypted with new master key │
│ 4. Legacy env var can be removed after migration │
└─────────────────────────────────────────────────────────────┘
Setup Guide
- New Installation: Launch Nudlers. The UI automatically detects that the vault is uninitialized and guides you through creating a passphrase. After setup, you'll be prompted to optionally register a passkey for biometric unlock.
- Legacy Migration: If you have
NUDLERS_ENCRYPTION_KEYset, the UI will guide you through migrating to the vault. All credentials are re-encrypted in a single transaction. You can remove the env var after migration.
Passkey Management
- Register multiple passkeys (e.g., laptop fingerprint + phone FaceID)
- View and delete individual passkeys in Settings → Vault Security
- When passkeys are registered, the vault defaults to passkey authentication
- You can always switch to passphrase entry by clicking "Use passphrase instead"
- Changing your passphrase invalidates all registered passkeys (re-register required)
Environment Variables for Vault
| Variable | Required | Description |
|---|---|---|
PASSKEY_ENCRYPTION_SECRET | Production | Required if using passkeys in production. A stable secret used to encrypt the vault passphrase stored in the database. Generate with openssl rand -base64 32. Must never change — rotating it invalidates all registered passkeys. |
WEBAUTHN_RP_ID | Production | WebAuthn Relying Party ID. Defaults to localhost. Must be set to your domain (e.g. nudlers.example.com) when running behind a reverse proxy or over HTTPS. |
WEBAUTHN_ORIGIN | Production | WebAuthn expected origin. Defaults to http://localhost:6969. Must be set to your full app URL (e.g. https://nudlers.example.com) when running behind a reverse proxy or over HTTPS. Without this, passkey registration/login will fail with an origin mismatch error. |
🍓 Runs Anywhere
From powerful servers to a Raspberry Pi — Nudlers adapts to your hardware.
| Mode | Target Hardware | RAM Usage |
|---|---|---|
| Normal | Servers, PCs | 2GB+ |
| Low | Synology NAS, QNAP, Raspberry Pi | 512MB+ |
🏦 Supported Institutions
Banks
| Hapoalim | Leumi | Mizrahi Tefahot | Discount |
| FIBI | Yahav | Otsar Hahayal | Beinleumi |
| Massad | Union | Jerusalem | Pepper |
| OneZero |
Native 2FA is built in for OneZero and Bank Hapoalim's OTP flow — no manual code-typing per sync.
Credit Cards
| Visa Cal | Max (Leumi Card) | Isracard | American Express |
🚀 Quick Start
Prerequisites
- Docker (recommended) OR Node.js 22+ with PostgreSQL 16+
- Google Chrome (for scraping, included in Docker)
Option 1: Docker (Recommended)
# Clone the repository
git clone https://github.com/enudler/nudlers.git
cd nudlers
# Configure environment
cp .env_example .env
# Edit .env with your database password
# Start everything
docker-compose up -d
Open http://localhost:3000 and start adding your accounts!
Option 2: NAS / Server (Pre-built Image)
For Synology, QNAP, or any server with Docker:
# Create deployment directory
mkdir nudlers && cd nudlers
# Download production configs
curl -O https://raw.githubusercontent.com/enudler/nudlers/main/docker-compose.prod.yaml
curl -O https://raw.githubusercontent.com/enudler/nudlers/main/.env_example
# Configure and start
cp .env_example .env
# Edit .env with your settings
docker-compose -f docker-compose.prod.yaml up -d
Supports both linux/amd64 and linux/arm64 architectures.
Option 3: Manual Installation
# Clone and install
git clone https://github.com/enudler/nudlers.git
cd nudlers/app
npm install
# Configure PostgreSQL and .env file
# See Environment Variables section below
# Run
npm run dev
⚙️ Configuration
Environment Variables
| Variable | Required | Description |
|---|---|---|
NUDLERS_DB_USER | ✅ | PostgreSQL username |
NUDLERS_DB_HOST | ✅ | Database host (nudlers-db for Docker) |
NUDLERS_DB_NAME | ✅ | Database name |
NUDLERS_DB_PASSWORD | ✅ | Database password |
NUDLERS_DB_PORT | Database port (default: 5432) | |
RESOURCE_MODE | normal or low (default: normal) |
Application Settings
All settings are configurable through the Settings UI (gear icon in navigation):
| Category | Settings |
|---|---|
| Language | Hebrew or English (RTL flips automatically) |
| Sync | Enable/disable, sync hour, days to fetch |
| Display | Currency, date format, billing cycle start day |
| Scraper | Timeout, show browser (debugging), category fetching |
| AI | Provider base URL, API key, model slug |
| Enable summary, send hour, recipients, summary mode, restart-locked notification | |
| Vault | Passphrase, passkeys, change-passphrase |
🤖 AI Integrations
Built-in AI Assistant
The built-in chat answers questions about your finances using any OpenAI-compatible AI provider:
- "What's my budget status for groceries?"
- "Show me all transactions from Rami Levy"
- "How much did I spend on dining this month vs last month?"
Setup: Open Settings → AI Provider and configure:
- Base URL — defaults to OpenRouter (
https://openrouter.ai/api/v1). Presets included for OpenAI, Groq, Together, Gemini, or paste any custom OpenAI-compatible endpoint. - API Key — bearer token for the selected provider.
- Model — provider-specific slug (e.g.
google/gemini-2.5-flash,openai/gpt-4o-mini,anthropic/claude-3.5-sonnet).
Or via env vars: AI_BASE_URL, AI_API_KEY, AI_MODEL.
MCP for Claude Desktop / Cursor / Claude Code
Nudlers exposes a Model Context Protocol (MCP) endpoint that AI assistants can use directly to query and manage your finances.
Setup for Claude Desktop
Add to ~/.config/claude/claude_desktop_config.json (macOS/Linux) or %APPDATA%\Claude\claude_desktop_config.json (Windows):
{
"mcpServers": {
"nudlers": {
"command": "npx",
"args": ["-y", "supergateway@latest", "--sse", "http://localhost:6969/api/mcp"]
}
}
}
Setup for Cursor
Add to ~/.cursor/mcp.json:
{
"mcpServers": {
"nudlers": {
"command": "npx",
"args": ["-y", "supergateway@latest", "--sse", "http://localhost:6969/api/mcp"]
}
}
}
Setup for Claude Code
Add to your project's .mcp.json or global ~/.claude/mcp.json:
{
"mcpServers": {
"nudlers": {
"command": "npx",
"args": ["-y", "supergateway@latest", "--sse", "http://localhost:6969/api/mcp"]
}
}
}
Remote / Hosted Setup
For Nudlers running on a remote server, NAS, or Docker container, replace the URL:
{
"mcpServers": {
"nudlers": {
"command": "npx",
"args": ["-y", "supergateway@latest", "--sse", "https://your-server.com/api/mcp"]
}
}
}
Examples:
- Docker on local network:
http://192.168.1.100:3000/api/mcp - Synology NAS:
http://nas.local:3000/api/mcp - Cloud server with HTTPS:
https://nudlers.yourdomain.com/api/mcp
Note: For HTTPS, ensure your server has a valid SSL certificate. For local network access, use HTTP with your server's IP address.
Available Tools
| Tool | Description |
|---|---|
get_monthly_summary | Get financial summary by vendor with income, expenses, and net balance |
get_category_expenses | Get all transactions for a specific category |
get_category_breakdown | Get spending breakdown by category with percentages |
get_all_categories | List all spending categories in the system |
search_transactions | Search transactions by description, vendor, or category |
get_all_transactions | Get all transactions for a time period |
get_budgets | Get budget vs actual spending comparison |
get_recurring_payments | List subscriptions and installment payments |
get_balance_projection | Get daily balance projection for the next 30 days |
get_sync_status | Check sync status for all connected accounts |
list_accounts | List all configured bank accounts and credit cards |
add_manual_expense | Add a manual expense or income transaction |
Example Queries
Once connected, you can ask your AI assistant:
- "What did I spend on groceries this month?"
- "Show me my budget status"
- "Add a manual expense: Coffee at Aroma, 25 ILS, today, category Dining"
- "What are my recurring payments?"
- "Search for transactions from Rami Levy"
- "Compare my spending by category"
Troubleshooting MCP
Connection refused:
# Verify Nudlers is running
curl http://localhost:6969/api/ping
# Should return: {"status":"ok"}
Test the MCP endpoint:
# This should return SSE headers and keep connection open
curl -N http://localhost:6969/api/mcp
"supergateway" not found:
# Ensure npx is available (comes with Node.js)
npx --version
# Or install supergateway globally
npm install -g supergateway
Wrong port:
- Development mode uses port
6969 - Docker production typically uses port
3000 - Check your
docker-compose.yamlfor port mappings
Firewall issues (remote access):
- Ensure the port is accessible from your client machine
- For Docker: check port mappings in
docker-compose.yaml - For NAS: check firewall and port forwarding settings
💡 Smart Categorization Explained
Nudlers uses a unique 3-phase approach to achieve high accuracy while avoiding bot detection:
┌─────────────────────────────────────────────────────────────────────┐
│ PHASE 1: Hybrid Scrape │
│ Fetch transactions WITHOUT categories (avoids bot detection) │
└────────────────────────────────┬────────────────────────────────────┘
│
▼
┌─────────────────────────────────────────────────────────────────────┐
│ PHASE 2: Local Matching │
│ ┌──────────────────┐ ┌──────────────────────────────────────┐ │
│ │ Custom Rules │ -> │ If no match, check historical cache │ │
│ │ (Regex-based) │ │ "Aroma" -> "Dining" (from history) │ │
│ └──────────────────┘ └──────────────────────────────────────┘ │
└────────────────────────────────┬────────────────────────────────────┘
│
▼
┌─────────────────────────────────────────────────────────────────────┐
│ PHASE 3: Selective Enrichment │
│ Only for remaining uncategorized: targeted API calls (low risk) │
└─────────────────────────────────────────────────────────────────────┘
This approach provides:
- Speed — Most transactions categorized instantly from cache
- Accuracy — 95%+ categorization rate
- Safety — Minimal API calls prevent account lockouts
📱 WhatsApp Integration
How It Works
Nudlers uses a headless browser to connect to WhatsApp Web — no third-party services required.
Setup
- Go to Settings → WhatsApp Daily Summary
- Click Start WhatsApp Service
- Scan the QR code with your phone (WhatsApp → Linked Devices)
- Configure recipients (phone numbers or group IDs)
- Set your preferred delivery time
Docker Configuration
For Docker deployments, add these to your docker-compose.yaml:
services:
nudlers-app:
volumes:
- whatsapp-data:/app/.baileys_auth # Persist Baileys session
cap_add:
- SYS_ADMIN
security_opt:
- seccomp=unconfined
shm_size: '2gb'
volumes:
whatsapp-data:
🛠️ Troubleshooting
"Block Automation" Errors (Isracard/Max/Amex)
These vendors have aggressive bot detection. Solutions:
- Use Low Resource Mode — Set
RESOURCE_MODE=lowto reduce browser footprint and memory usage - Reduce Sync Days — Lower
sync_days_backto 7-14 days - Manual Login — Log in to the vendor website once to clear notices
- Wait — If blocked, wait 24 hours before retrying
Chrome Not Found
For custom environments:
PUPPETEER_EXECUTABLE_PATH=/usr/bin/google-chrome
WhatsApp QR Code Not Appearing
- Check browser capabilities in Docker config
- Ensure
shm_sizeis at least1gb - Check logs:
docker-compose logs -f nudlers-app
🏗️ Architecture
nudlers/
├── app/ # Next.js application
│ ├── components/ # React UI components
│ │ ├── CategoryDashboard/ # Main dashboard views
│ │ ├── Layout.tsx # App shell with navigation
│ │ └── ...
│ ├── pages/
│ │ ├── api/ # API routes
│ │ │ ├── transactions/ # Transaction CRUD
│ │ │ ├── scrapers/ # Scraper control
│ │ │ ├── reports/ # Financial reports
│ │ │ ├── anomalies/ # Insights inbox + manual evaluator
│ │ │ ├── mcp.ts # MCP integration endpoint
│ │ │ └── ...
│ │ └── index.tsx
│ ├── scrapers/ # Bank scraper logic
│ ├── utils/ # Shared utilities
│ └── styles/ # Theming (light/dark mode)
├── docker-compose.yaml # Local development
├── docker-compose.prod.yaml # Production deployment
└── db-init/ # Database initialization
Tech Stack
| Layer | Technology |
|---|---|
| Framework | Next.js 16 (Pages Router) |
| Language | TypeScript |
| Database | PostgreSQL 16 |
| UI | Material-UI v6, CSS Variables |
| Scraping | israeli-bank-scrapers, Puppeteer |
| AI | OpenAI-compatible (OpenRouter default), MCP SDK |
| Messaging | Baileys (WhatsApp), Telegram Bot API |
| Testing | Vitest, Playwright |
🧪 Development
cd app
# Install dependencies
npm install
# Start development server (port 6969)
npm run dev
# Run tests
npm run test
# Run linter
npm run lint
# Start Storybook (port 6006)
npm run storybook
🔄 Updating
Docker
docker-compose pull
docker-compose up -d
Manual
git pull
cd app
npm install
npm run build
npm start
Database migrations run automatically on startup.
📄 License
Polyform Noncommercial License 1.0.0
Free for personal, non-commercial use. For commercial licensing, please contact the author.
See LICENSE for full terms.
🙏 Credits
- Bank Scraping: israeli-bank-scrapers
- UI Framework: Material-UI
- WhatsApp Integration: Baileys
Take control of your Israeli finances.
nudlers.com •
Star on GitHub •
Report Issues