npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

israeli-banks-actual-budget-importer

v1.10.4

Published

[![semantic-release](https://img.shields.io/badge/%20%20%F0%9F%93%A6%F0%9F%9A%80-semantic--release-e10079.svg)](https://github.com/semantic-release/semantic-release) [![XO code style](https://shields.io/badge/code_style-5ed9c7?logo=xo&labelColor=gray)](ht

Readme

Israeli Banks → Actual Budget

semantic-release XO code style Snyk Security CodeQL OpenSSF Scorecard

This project provides an importer from Israeli banks (via israeli-bank-scrapers) into Actual Budget.

Features

  1. Multi Bank Support
    Supports all of the institutions that the israeli-bank-scrapers library covers (Bank Hapoalim, Cal, Leumi, Discount, etc.).

  2. Prevents duplicate transactions
    Uses Actual’s imported_id logic.

  3. Automatic Account Creation
    If the bank account does not exist in Actual, it will be created automatically.

  4. Reconciliation
    Optional reconciliation to adjust account balances automatically.

  5. Credit Card / Multi-Account Mapping (Targets)
    Supports mapping multiple scraped accounts/cards into one Actual account, or mapping each scraped card into its own Actual account (via targets and accounts).

  6. Concurrent Processing
    Uses a queue (via p-queue) to manage scraping tasks concurrently.

  7. Pending transactions are skipped
    Only completed transactions are imported into Actual, which avoids provisional card amounts and pre-conversion foreign-currency rows landing in the final ledger.

Installation

Docker

https://hub.docker.com/r/tomerh2001/israeli-banks-actual-budget-importer

Example

services:
  importer:
    image: tomerh2001/israeli-banks-actual-budget-importer:latest
    restart: always
    cap_add:
      - SYS_ADMIN
    environment:
      - TZ=Asia/Jerusalem
      - SCHEDULE=0 0 * * * # Optional (Used to run periodically - remove to run once)
    volumes:
      - ./config.json:/app/config.json
      - ./cache:/app/cache # Optional
      - ./chrome-data:/app/chrome-data # Optional (Used to solve 2FA issues like with hapoalim)

Actual version compatibility

This importer bundles a specific @actual-app/api version, and Actual versions the API package and the server together.

If you upgrade your Actual server, upgrade this importer image as well. A stale importer image against a newer Actual server can fail during startup with errors such as out-of-sync-migrations.

The importer now checks the server version before downloading the budget and fails early with a clear mismatch message that includes both versions.

Configuration

The application configuration is defined using JSON and validated against a schema.
The main configuration file is config.json.

The configuration has two independent top-level sections:

  1. actual – Configures the Actual Budget connection.
  2. banks – Configures bank scrapers and account mappings.

1) actual section

This section configures the connection to your Actual Budget server and budget.
It is always required, regardless of how you configure banks or targets.

{
  "actual": {
    "init": {
      "dataDir": "./data",
      "password": "your_actual_password",
      "serverURL": "https://your-actual-server.com"
    },
    "budget": {
      "syncId": "your_sync_id",
      "password": "your_budget_password"
    }
  }
}

Nothing in this block changes when using targets, credit cards, or multi-account mappings.


2) banks section

The banks section defines:

  • Which banks to scrape
  • The credentials for each bank
  • How scraped accounts/cards are mapped into Actual accounts

Each bank entry includes the credentials required by israeli-bank-scrapers (e.g. userCode, username, password, etc.).


targets sub-section

A single bank scrape (for example visaCal) may return multiple accounts/cards.
Different users model these differently in Actual, so the importer supports targets.

Each target represents:

  • One Actual account
  • One or more scraped accounts/cards that feed into it

For each target:

  • Imported transactions = concatenation of transactions from selected cards
  • Reconciliation (if enabled) = sum of balances of selected cards
    (only cards with a valid numeric balance are included)

Reconciliation behavior

  • Reconciliation is controlled by the reconcile boolean.
  • When reconcile: true, a new reconciliation transaction is created on every run (no updates, no reconciliation).
  • Existing reconciliation transactions are never modified or reused.
  • If reconcile is omitted or set to false, no reconciliation transaction is created.

Example A: One Actual account for all VisaCal cards

{
  "actual": {
    "init": {
      "dataDir": "./data",
      "password": "your_actual_password",
      "serverURL": "https://your-actual-server.com"
    },
    "budget": {
      "syncId": "your_sync_id",
      "password": "your_budget_password"
    }
  },
  "banks": {
    "visaCal": {
      "username": "bank_username",
      "password": "bank_password",
      "targets": [
        {
          "actualAccountId": "actual-creditcards-all",
          "reconcile": true,
          "accounts": "all"
        }
      ]
    }
  }
}

Example B: One Actual account per VisaCal card

{
  "actual": {
    "init": {
      "dataDir": "./data",
      "password": "your_actual_password",
      "serverURL": "https://your-actual-server.com"
    },
    "budget": {
      "syncId": "your_sync_id",
      "password": "your_budget_password"
    }
  },
  "banks": {
    "visaCal": {
      "username": "bank_username",
      "password": "bank_password",
      "targets": [
        {
          "actualAccountId": "actual-card-8538",
          "reconcile": true,
          "accounts": ["8538"]
        },
        {
          "actualAccountId": "actual-card-7697",
          "reconcile": true,
          "accounts": ["7697"]
        }
      ]
    }
  }
}

Example C: Grouped cards into a single Actual account (subset)

{
  "actual": {
    "init": {
      "dataDir": "./data",
      "password": "your_actual_password",
      "serverURL": "https://your-actual-server.com"
    },
    "budget": {
      "syncId": "your_sync_id",
      "password": "your_budget_password"
    }
  },
  "banks": {
    "visaCal": {
      "username": "bank_username",
      "password": "bank_password",
      "targets": [
        {
          "actualAccountId": "actual-cal-primary",
          "reconcile": true,
          "accounts": ["8538", "7697"]
        }
      ]
    }
  }
}

Legacy configuration (single Actual account per bank)

This configuration style is fully supported for backward compatibility,
but does not allow fine-grained control over multiple cards/accounts.

It maps all scraped accounts from the bank into a single Actual account.

{
  "actual": {
    "init": {
      "dataDir": "./data",
      "password": "your_actual_password",
      "serverURL": "https://your-actual-server.com"
    },
    "budget": {
      "syncId": "your_sync_id",
      "password": "your_budget_password"
    }
  },
  "banks": {
    "hapoalim": {
      "actualAccountId": "account-123",
      "userCode": "bank_user",
      "password": "bank_password",
      "reconcile": true
    },
    "leumi": {
      "actualAccountId": "account-456",
      "username": "bank_username",
      "password": "bank_password"
    }
  }
}

Notes

  • The actual block is always required and independent of bank configuration.
  • targets are optional but strongly recommended for credit-card providers.
  • Duplicate transactions are prevented using a stable imported_id.
  • Credit card balances are often negative; reconciliation uses the values as returned by the bank.

License

This project is open-source. Please see the LICENSE file for licensing details.

Acknowledgments

  • israeli-bank-scrapers: Thanks to the contributors of the bank scraper libraries.
  • Actual App: For providing a powerful budgeting API.
  • Open-source Community: Your support and contributions are appreciated.