Building a Virtual Wallet in Laravel Just Got Easier

Laravel Virtual Wallet, digital balances, Laravel app

If you’ve ever tried building a wallet system in Laravel — like for in-app purchases, balance top-ups, or digital credits — you know it’s a bit of a pain. There’s a lot to keep track of: balance management, deposits, withdrawals, transactions, currency formatting, even rounding issues.

So when I came across this new Laravel Virtual Wallet package, I got a little excited (okay, maybe a lot). This package basically wraps all the painful stuff in a clean, easy-to-integrate interface that just works. I gave it a try, and here’s what I found — the good, the gotchas, and whether I’d use it again.


Why You Might Want a Virtual Wallet System

There are plenty of use cases for virtual wallets:

  • Loyalty points in e-commerce apps
  • Token systems for games or education platforms
  • Internal currency for SaaS products
  • Digital credit for services like food delivery or ride-sharing

You could build it from scratch — but why reinvent the wheel if someone else already built the spokes, rim, and hub?

That’s where Laravel Virtual Wallet comes in.


What the Package Actually Does

This package gives you an easy way to attach a wallet to any Eloquent model (like User), and then perform operations like:

  • deposit()
  • withdraw()
  • forceWithdraw()
  • transfer()
  • balance()
  • transactions()

All wrapped in a nice API-style method chain you’d expect from Laravel packages.

The core logic lives in a HasWallet trait that you drop into your model. So if you want to give a User a wallet:

use Bavix\Wallet\Traits\HasWallet;

class User extends Authenticatable
{
    use HasWallet;
}

That’s it. No boilerplate, no extending weird base classes. Clean.


Installing the Package

Here’s the install flow I used:

composer require bavix/laravel-wallet

Then publish and run the migration:

php artisan vendor:publish --tag=wallet-migrations
php artisan migrate

Done. Now your database has the tables it needs for wallets and transactions.

Pro tip: You can customize table names and models in the config if needed.


Real-World Usage: Deposit & Withdraw

Let’s say you want to top-up a user’s balance. With this package, it’s literally one line:

$user->deposit(500); // adds 500 units (e.g. cents, points, tokens)

Need to deduct something?

$user->withdraw(200); // subtracts 200 units

Worried about overdraws? Don’t be. The package throws an exception if there isn’t enough balance.
Unless you want to override that (which you can, with forceWithdraw()).

You can also do transfers between users:

$userA->transfer($userB, 150); // move 150 from A to B

And yes — everything gets logged in a transactions table, including transfer logs, amounts, timestamps, and wallet IDs.


What’s Stored in the Database?

Two main tables:

  • wallets: tracks each model’s balance and currency
  • transactions: logs all movements (deposit, withdraw, transfer, etc.)

The cool part? It stores amounts in raw integers — perfect for avoiding floating-point nightmares. So if you’re dealing with money, always treat values as cents, not dollars.


Multiple Wallets Per Model?

Yes. This part kinda blew my mind.

You can assign multiple named wallets to a single model. For example, a user might have:

  • main wallet
  • bonus wallet
  • referral wallet

Here’s how to use them:

$user->createWallet([
    'name' => 'Referral Wallet',
    'slug' => 'referral',
    'meta' => ['type' => 'promo']
]);

$user->wallet('referral')->deposit(300);

Now that’s flexible. I immediately thought of loyalty programs, games, and promo campaigns.


Currency Support

Out of the box, it doesn’t handle multiple currencies yet, but you can customize that in the config if needed.

The stored amounts are numeric only, so formatting is up to you (hint: use moneyphp/money if you need hardcore currency logic).


Event Hooks and Observers

One thing I appreciate is how the package fires model events — so you can hook into stuff like:

  • TransactionCreated
  • WalletCreated
  • BalanceUpdated

Useful if you want to trigger things like notifications, audits, or logs. You can even extend or override the core logic if needed.


What I Liked (and What Could Be Better)

👍 What I Loved:

  • Super easy to set up
  • Intuitive API methods
  • Solid database design
  • Supports decimal precision and rounding
  • Multiple wallets per model — seriously cool

🤔 Room for Improvement:

  • Docs are a bit sparse in some advanced areas
  • Custom transaction types require some digging
  • No built-in UI (but that’s fair — it’s backend-focused)

Final Thoughts

If you’re building anything that involves tracking virtual balances — whether it’s coins, credits, or points — this package is a solid time-saver.

You don’t have to worry about concurrency issues, math precision, or creating transaction logs manually. It’s all handled behind the scenes. And Laravel devs will feel right at home thanks to the trait-based setup and familiar API design.

Would I use this in a real project?
Absolutely. In fact, I already am.


Pro Tip:
Store all balances in integers (like cents or tokens), and let your frontend handle the formatting. It’ll save you from money-related headaches down the line.

Leave a Comment

Your email address will not be published. Required fields are marked *

Scroll to Top