jorisvanandel's avatar

Best practice for models with lots of relations/calculations

I am building a SPA application using Vue/Laravel. It is a financial application with a lot of models two of which are important for this matter, namely Users and Transactions. A Transaction can be booked on a User which mutates the 'balance' property of the User. It is possible that there will be hundreds of Users each of them with at least a hundred Transactions booked on them.

I was wondering what the best architecture for this project would be.

I have two options in mind:

  1. Add a 'balance' property to the User's table and update this property every time (more code and bugs)
  2. Add a 'balance' property as a getter method to the User model and calculate it's balance everytime the user is fetched (less code/bugs but worse performance)

When using method 2, I quickly found out that fetching all users took quite a bit (3-4 seconds with just 30 users and 500 transactions). Maybe my code is inefficient? The getter method was just something like

foreach ($this->transactions() as $transaction) { $total += $transaction->amount; }

The balance would be updated quite often so caching the result of 2 wouldn't help a lot because I'd have to flush the cache everytime a transaction is booked/created/updated.

0 likes
1 reply
alanholmes's avatar

If you are going to have a lot of data, then method 1 would probably be the best way (IMO) - as you are just aggregating the data, so it only needs to be recalculated when a transaction is added.

Not sure how complicated you want to make this, but you could look at something like this: https://docs.spatie.be/laravel-event-projector/v2/introduction/

Or you could have a more simple system, where adding a transaction fires an event, which will then trigger code to update the balance.

Please or to participate in this conversation.