How to Track Running Balances in Bubble.io (The Right Way) – ratio.dev

Dennis H. Lewis shows how to track running balances correctly in Bubble.io by building a FIFO queue and database triggers to process updates sequentially, since Bubble's parallel workflows can corrupt data. The method uses four tables, marks queue items with statuses, and locks accounts during recalculations to prevent race conditions.
Chapters
How can you keep track of accurate balances in your bubble application? What do I mean by that? Imagine that you have created an awesome bubble application to manage your checking account. Every day you're entering in new transactions and you need to know at every moment how much money you have in your account available. Even more, you want to be able to look back and see how your balance evolved over time. So across the month or from the beginning of the year, has it grown, has it shrunk? It sounds simple. Well, you're going to see in this video that symbol is not. But you're also going to learn exactly how to accomplish just this. I'm going to walk you through step by step so that you can see how to set up your database. You can see what workflows you're going to need to create, what specific scenarios you're going to need to keep in mind in order for all of this to work together. So let's just jump in and get started. First, let's look at the database structure. And you're going to need four tables for this process. Okay. The first is an account table. So this is where you're going to keep track. Is it your checking account? Is it your savings account, Is it Your investment account? 1 row for each account. You're going to need another table where we keep track of our daily balance. So we're going to call that the account balance table. And this table is going to have. It's going to have an account, it's going to have the balance, it's going to have a date so that you can have a daily balance. And it's going to have your month, week, and your year. And we'll see why about that later. We also need a transaction table. So that is where we're going to keep all of the transactions that happen in our application. So they're going to be associated with an account as well. They're going to have an amount, which is the dollars and cents. We're going to keep track of when they happen, the date. There's going to be a description. You can have more fields, whatever you need in there. And we'll see how we're going to use the transactions to maintain our accurate balances over time. And then finally, we're going to need a table called the Balance Calculate Q. And that's going to be really important for how this all works together. But before we talk about that, let's think about what some of the difficulties are that you really have to take into account when you're trying to maintain balances. So at first glance, keeping track of each account's balance seems simple. Every time you process a transaction, you add or subtract the amount of that transaction from the latest balance and yeah, that's it, right? Sounds like that's all you really need. Easy enough. But what happens if there isn't a row in your account balance table because you haven't had any transactions that day? What happens if the user decides to go back two months back and change a transaction? Ooh, that one's a bad one. What happens if the user very quickly starts making changes to several different transactions or adding in a bunch of transactions pretty quickly together? All of these things are important for figuring out how we're going to set up our application in bubble so that we don't get everything all messed up. And let's face it, why does bubble also make this a little bit more difficult than what you might expect? First of all, bubble loves to execute workflow steps in parallel. Okay, so when you open a, when it starts a workflow, they all go at the same time. And if you have three workflows that on the back end running, they'll run to all at the same time. And if you do a run of schedule a workflow on a list of items, boom, they'll run in parallel. All of this is great for making things zippy and fast, but for calculating balances, it can be a nightmare. And bubble also lacks a lot of the basic database functions that a normal relational database would have. So having a, what we call a transaction window where you can have a commit or a rollback at the end, you know, will undo everything if it didn't finish correctly. Can't do that in bubble. It doesn't have any way of blocking a row. So two different workflows can be trying to change the same row in your database table at the same time. It doesn't have a forced integrity. So if you know, you create a relationship and you delete the parent, then the child can be left or orphaned. All of these things make managing your bubble database more tricky than an old fashioned relational database would be. But don't get worried, I've got your back. Because in this video I am going to show you an ironclad way to handle all of, and to resolve all of these issues. We're going to have to roll up our sleeves and do some kind of special stuff. So the first thing we're going to have to do is we're going to have to build a backend transaction queue that we can use so that all the process transaction balance calculations happen sequentially in order and one after the other so that they don't skimp on top of each other. We are going to need to create a database trigger that identifies if we're adding in a new transaction or we're modifying an old one. We're going to need a process whereby we recalculate all the subsequent transactions if we've modified something in the past. Okay, and that's. There's no way around it because if I had a. I put in a check in my checking account and I said it was a thousand dollars six months ago, and then six months later I realized, oh, that wasn't a thousand dollars, that was a hundred dollars. From there on I'm $900. My balances are $900 off. And there's no alternative other than to go back and recalculate all of those balances so that they're accurate again. And we're also going to need to implement a recursive work though, that recalculates all of these transactions one to one in order so that. Because you don't want to be jumping around in order because then your balance won't be correct either. And then there's going to be a few extra bonuses that are going to serve you well in the future that you're going to learn in this video. You're going to learn how to use custom events to reduce the number of searches in your workflows. That's always good. That will save you some money. And we're also going to learn how to use custom events to make sure that your workflow steps execute in order. So now that we have an idea of what we're going to do, stick with me. And we're going to just dig into it from the very beginning. This isn't going to be a short video. Okay? I'm warning you. There's a lot that we have to go over and it can be a little bit tedious at times, so you may have to go back and rewind and watch things a couple of times. But I have spend a lot of time preparing the structure of this video so that you won't miss out on anything critical and you can get to the final port of call safely. So this first step we're going to do is we're going to create a database trigger for our transaction table. Okay? So I'm going to go in here to my backend workflows and I'm going to look at here a.
Trigger that Database trigger that I have created that only executes if the before amount is different from the after amount. So here we have, I've called this transaction amount and it is a database trigger. So when I that means it will automatically bubble will automatically. Every time the transaction table is changed, it will look and it will look at this condition and say is the amount of this traction has the amount of the transaction changed? Okay, so you database triggers have two instances. You can see the before and the after. Okay. The before and the now is what it's called. Okay, so this database trigger is only going to execute if the before changes amount is not the now amount. So the amount, because if the amount is the same, doesn't affect our balances. We don't have to do anything. Okay. First what we're going to do is we're going to store the previous amount. Okay. And we're going to see why a little bit farther down the road. But if we're going to be making changes, if it's a modification, we don't. We have to know the difference between what it was before and what it is now. And the only way to do that is actually store the previous amount. So that's the first step that this trigger is going to do. And it's going. So if you look at this, it's as simple as pulling in here and saying previous amount is equal to transaction now's amount minus transaction before's amount. So that's the difference. And I put it into previous amount. If this is a new transaction, then it's transaction. The amount before is going to be zero, empty. So subtracting zero isn't going to change it. I'm going to have a zero in that in the previous amount and that's not going to be any problem there. And then the next thing we're going to do is we are going to schedule a workflow, a backend workflow to create a new entry in our transaction in our back end queue. We're going to say, okay, I have a transaction whose amount has changed. We need to fix the balance. Okay. And the way we're going to do that is to write a row into our queue table and then our transaction queue is going to process that independently. Now it's important that we schedule this in another API workflow. Why is that? Because bubble won't trigger another database trigger from inside one because it could get really complicated. So in this case, the way you do that is you schedule it into a different backend workflow. And so now it's not the database trigger triggering another one. It's a independent process and that's how you solve that little problem. So now let's break down this backend workflow that we've called transaction, right? Valq. Okay? So transaction, write a balancequeue calculation row, okay? And the first thing that we're going to do is, is we are going to trigger a custom event that calculates the number of subsequent transactions that come after this. This transaction that we've just seen has been changed. And.
The reason we're going to do that is because that way we're going to be able to know if this is just a new transaction and all we have to do is update the balance with it, or if it's going to affect future a whole bunch of other transactions that we're going to need to recalculate those as well. So that's the first step is we're going to trigger this custom event. And one of the important things about database triggers are about triggering custom events is that they finish that they force bubble to be to go step by step. So step two and step three will not execute until after this custom event has finished. Really an important thing to know about how bubble workflows work. So if we look at this and this custom event and it's called transaction number after, okay, and this is actually a very simple little custom event, all it's going to do is it's going to take an input for a transaction and it's going to return a numeric value of the number of transactions that come after it. So all it does, it has one step that is a return data and is a search. So I'm going to do a search for all of the transactions that use this account by the same user whose date is post is bigger than the date of the transaction that I'm looking at. So if there's any more, I want you just to tell me, do the search and return the count the number of rows. Okay? So that's a pretty simple, straightforward step here. One thing I do want you to understand in this whole example is that the queue is going to work by user and account. So it doesn't matter to me if this application is calculating the balance of somebody else's transactions. They're not going to affect mine at all. Let it do it in parallel, that's fine. In fact, I'm not even going to worry if I have multiple accounts for my user and it's calculating their balances at the same time also doesn't make any difference. But I do want to make sure that my queue is always respecting for one account and one user. There's only going to be one balance calculation going on at a time. So that's what the how the queue is working. So once I've returned this number, we're back here, and then we're going to have two steps and one is going to be either based on if the number of transactions is less than 1, so there's no other transactions afterwards, or if there's more than one transactions afterwards. The way we write the row in the Q table is going to be slightly different. So if there aren't any more coming afterwards, all I'm going to do is I'm going to say, okay, we need to do balance calculation for this account. We're going to leave the completed date empty. We're going to put the starting date empty. We're going to set it as status pending. So it hasn't done anything, it's just waiting to be completed. And this is the transaction that you need to calculate the balance for, and this is its date. Okay, simple. That's what we're going to do. Go off and rewrite that row into the queue and we'll worry about later how the queue actually processes it and does its work. If there are subsequent transactions, there's more of them that have to be recalculated. Then I'm going to make a very similar row in the queue, but I'm not going to include the actual transaction, I'm just going to include the date. That's going to be my indicator of whether I need to just calculate one, the balance for one transaction, or if I need to calculate a whole bunch of them. Okay, so that's how we're going to set up the. The row in the Q table, which is the balance calculate Q. And that will be the.
Place where our boundaries calculations are all going to get started from.
All right, the next step that we're going to do is we are going to talk now about the balance calculation Q and how it works and how we set it up so it actually does its job.
This is a really powerful way of solving a particularly thorny issue with bubble applications. How do we create an ironclad method of making sure that our balance calculations process consecutively without stepping all over themselves? Now, if it were just one process at a time, we could do it with a recursive workflow and that would be good enough. But here's the problem. What about if I go back and change a transaction six months ago and Then I also find another error three months ago and I make that change and the six month ago one hasn't finished and now it's got two recursive workflows working in the same account at the same end. It's just going to be a mess and it's just not going to work. So that's where the balance calculation queue comes in. A backend work for you. Workflow queue is just like waiting in line at the supermarket until the little old lady in front of you finishes taking out her coupons and getting out her Visa card and giving it to the lady, to that checkout clerk you are, it won't be your turn to pay and you're just going to have to patiently wait. This is called a first in, first out queue because the jobs are processed in order, in the same order that they are created. So first the little lady and then you. Since Bubble doesn't have a native queue functionality, we're going to have to build it for ourselves. And that's why this video is going to be longer than you, than I anticipated. But I think you're going to learn a lot of stuff in here as well. For example, our queue is only going to separate the recalculations by user and account. So let's jump into the Bubble builder and look at first of all the balance queue table. So let's go back into the database section and look at the balance queue table. And what it has is the account, the completed date, which is when something has, when a it's that row has been processed and it's done with the started date, which is also a date time, which is when it actually starts calculating the status. The status is fundamental here. It can either be pending, calculating, complete or failed. And we're going to see how that works. It can point to a transaction, might not if it's a whole bunch of them. And it can have a start date, which is saying, I want you to do the ones after this date, okay? And then it has the creator, which is the user. So those are all the fields that we need to have to make this, this process work. So now we're going to go look in the nitty gritty at the workflows and how all these fields work together to become an actual functioning queue. So how do we actually manage the queue so that it actually does what we want it to do? First of all, we need a mechanism that keeps the queue going. And that mechanism is going to be another database trigger, which we're going to, which we've Called queue status change. So I'm going to go back into backend workflows and I have a folder here with the transaction queue and I have a database trigger called queue status change. And this only executes when the balance calculate queue now status. Its now status is not its before status. So that means that every time the status changes on an element in the queue, this database trigger is going to execute and it's going to do follow the same process every time. Okay, but this is going to make sure that our queue keeps going. If you write a new row in there, that means it has a and you put it in with pending. Now there is a new row with pending. It's going to look the previous status didn't exist, so they're not the same. And it's going to start and if it changes to calculating or changes to completed, that's just going to keep it keep the process going. The trigger has just two steps. Step one is it's going to trigger a custom event called QChuck, which we're going to see in just a minute. And the second one is called a custom event called queue process. And this is the custom event that is going to process the next queue item and that is the value that QCheck is going to give us. So let's look at the definition of QCheck. QCheck takes user and account, which were the key fields that we said we're going to base the queue off of. And it returns a status and most importantly it returns an item from the queue and they're both optional because it may there may not be one. So that's fine. When it does, the first thing it's going to do is it's going to execute a custom event called trigger queue calculating. All it's going to do is it's going to do a search for the balance queue and it's going to say is there.
Any queue item for this user and for this account that is marked status calculated? And if it is, then I'm going to return the first one that is going to tell our trigger whether or not it's currently calculating the balance for something else for another queue item. That's all this is going to do. QCheck is going to return the Q item that is currently calculating if it exists for this user and this account. It's going to return a status of ready and then it's going to do a search and it's going to find the first one and it's going to return it. So it's going to say this is the next item in the queue that should be processed because it's not calculating anything. So let's look and see if there's one that's ready to go. If there is, that's the one we're going to do. If it doesn't find one, it'll return empty. That's okay too. Q will just sit there. That's all it. It doesn't need to do anything. There's no more work to be done. However, if there is one calculating, we need to make a check here because what if something went wrong in our balance calculation? I don't know, bubble servers went down, lightning struck, whatever. You didn't contemplate some special case in your workflow and it crashed. Well, if we're not careful, that means that our queue could get blocked and it would have one in there saying it's calculating for all of eternity and it would never keep going because that one ended, it never got cleaned, and now we've got a mess. So to avoid that, what we're going to do is we're going to say if Q calculating gave us back a result so it's not empty, and the result, the one it gave us back, it's calculated when it started has been more than X number of minutes. In this case, I've said 10 minutes, then I am going to say that this one has failed. Okay? Because I want to be sure that sufficient time down the road that my queue doesn't get blocked forever. So if it started more than 10 minutes ago and it hasn't finished, I'm going to mark it as failed, and that's going to trigger this new custom event called Q failed. And if we go look at Q failed, it's pretty simple what it does. It takes a queue item as an input. What it's going to do here is it's going to make a change to it. It's going to mark it as failed. So now it's no longer calculating. So that's what's going to unblock the cube because now there's no more calculating and it's going to mark the completed date as the current date time. So now I know when it was marked as failed. And then just for my personal use here, I'm going to send myself an email and I'm going to give it some data there so I can go in as the developer and see why did this queue item fail. I can go back into some triage and look and see what happened and hopefully identify what the problem was. So that is everything that QCheck does. The normal thing would be that there's nothing calculating, it's found one, it returned the next one from the list. And what is going to happen now from our trigger, our database trigger, after it does Q check, it's going to look and it's going to say if queue check has returned a queue item, so what the result of step one is not empty. What I'm going to do is I'm going to trigger the custom event queue process and I'm going to pass it this new one so that it can get started. So that's just passing the baton to the next pending item in the queue. And once that goes, then we would go to queue process. And here is where we actually start the work of calculating the balances. So let's see exactly how queue process this custom event works. The first thing it does is it's going to be now is when we're going to take into account whether or not it is just doing one transaction or it's refreshing a whole bunch of transactions because it was made in the past and we have to take it into account. The first thing we're going to do is we're going to look at the queue item that we've been sent. So transaction process, remember has received as a parameter a queue item. And if this queue items transaction is not empty, then I'm going to schedule an API workflow called Transaction Update Balance and we're going to see that in just a minute how it works. But if it is empty, then I'm going to trigger a different backend workflow which is called Refresh Account Balances Date, which is going to do the whole refresh from that date forward so that everything is recalculated correctly. And then once I've set those up, I am going to take this queue item and I'm going to flag it as calculating and I'm going to mark the started date as the current date time. So now my queue item is now marked as calculating and I have the date time when it started because that's going to be important because if the next one comes up and it's been 25 minutes, it's going to flag it as failed because we had a 10 minute limit. That is how the actual process of the backend queue works. I understand that there's a lot of little moving pieces in here, so you may have to go back and look back and forth and look at the screen and look, look at the, the different workflow. So now let's look at actually how both of these workflows work so that we can actually close the loop and get our entire process to calculate balances correctly. This workflow is called Transaction Update Balance. So that is over here. Let's look at Transaction Update Balance Input every transaction and a qid. This is a two step workflow. The first thing it's going to do is it's going to trigger a custom event called Adjust the balance. And then the second step is it's going to mark the queue item as complete and it's going to record the completed date time. So really this first step is going to do the work and the second step is going to say that the work was done correctly and we will flag the queue item so that it's marked as complete. You can see here that we're being really careful to make sure that our status field is always changing when it has to change so that our queue is going to be able to keep processing rows without ever getting mixed up. So let's look at how do we actually calculate the balance and what do we need to take into account. So let's go to this, this custom event called Trigger Adjust. We're going to Trigger Adjust balance. Okay. And this custom event takes an account, an amount and a date. So we're going to, we set it up this way because we're going to use this same functionality in the other workflow when we're doing a bunch of barrels adjustments. But in this case it doesn't matter. It takes an account, an amount and a date. Okay. And what does it do with it? Okay, the first thing it needs to do, and you'll see here that I think you'll start seeing that we separate these out into custom events because I want to make sure that they happen in order and that they finish before the next one starts. So this is a two step workflow and the first one is Adjust balance Record.
Adjust Balance Record. Let's look at it in detail. It takes two input fields, an account and a date and it returns a row from the account balance table. This is really important because this is going to take care of that case where I said what happens if there isn't a balance for today? Because there haven't been any transactions today, what do we do there? Because I can't just update the balance because it doesn't exist. So this is how we take care of this. In this workflow we're just going to find or create the row in the balance record table that we need. Notice that the account Balance the value that we're returning. I have marked it as optional. Okay. This is important in this case because there's going to be two different cases in the workflow. And so in order to be able to have more than 1 return data in the event it has to be optional, otherwise bubble won't let you have more than one. So the first thing we're going to do is if we're going to do a search and we're going to look for the account balances table for this account created by this same user, these are our keys and we're going to look at it and see is there a date that is equal to the date that I've been given? But now we have to be really careful about something and this is going to be really important with the date field. I can't just stick date into the balance table. If I do, there's going to be a new balance for every transaction because first one was at 3:00pm and the next one was at 3:15pm and the next one was at 4:00pm I want my account balance table to have exactly one row for each day that there's movement. So what I do is I compare it and I change the hours to zero, change the minutes to one and the seconds to zero and I look and see is there one already? Does one exist? And if the number is less than one, so it's zero, that means there isn't one for this account, for this user on this day, not date exactly. It's not an equal, but it's date is equal to. With those changes I made, then what I'm going to do is I am going to create a new row in the account balance table. I'm going to create it for this account. I'm going to set the date to the date of our transaction, but I'm going to change the hours to zero, change the minutes to one and change the seconds to zero. So that way I know it's always going to be the same. It's going to have the day and the time doesn't make any difference there. I'm also going to extract the month out of the date. I'm going to extract the week and I'm going to extract the year. Why do I do that? Because that's going to make filtering. If you want to be able to show the balances for a certain month and you want to be able to look at the balances by week or by year, it's going to make it easier for you down the road. So that's why I put those fields in and I calculate them here and now. The last important thing to take into account is the starting balance for today has to be the same as the last ending balance previously, okay? Because I can't start the day with a zero balance because yesterday I had $500 in my checking account. So now I have to say I'm starting off with whatever was in the very last one. So what I'm going to do here is I'm going to do a search for my balances table. I'm going to look for this created by this user, this account. And I'm going to look that the date is prior to the date of the transaction I'm working with and I'm going to sort them descending by date. So the first one is the most recent one before the one I'm looking at right now. I'm going to take that search, I'm going to get the first items balance and that's what I'm going to store into this new row in my account balances table. And then if the result of step one is not empty, that means that it actually had to create a new row that I'm going to return that new row that it made back to the adjust balance workflow. Okay? That's the value I'm going to return. However, if it is empty, so that means that step one didn't create a new row because there was already one, so didn't have to create one. Then what I'm going to do is search for the one that exists the same account, the same user, the same date is equal to the date I've been given, changing the hours, the minutes and the seconds and I'm going to get the first one, okay, because there's only going to be one and then I'm going to return that one and that's going to take us back here to the adjust balance workflow. So the first thing I did was was I found the record. So this is the one that came back. So it's now has either one that was created new or the one that already existed in the database. And all I have to do now is take the result that I got from step one, it's that account balance and I just change the balance to B this account balances. So it's current balance. So if it was $500 yesterday and it's just created a new one, then it's going to be 500 plus the amount that I've been sent. So if this is $100 deposit, then now I'm going to have a balance of 600 if it was $100 payment. Now I'm going to have a balance OF 400. All I've done is changed that balance and that has completed the adjust balance custom event. Remember we were looking at transaction update balance. So that is the step one. We have now adjusted the balance and now for step two, we marked it complete and we put the completed date time and that's finished. That has processed the transaction, it's updated the balance and that queue item is done. Good for us there. Now we're going to have to look at the more complicated process is when we have to refresh a whole list of transactions because somebody smart went back and made a change to a transaction six months ago. And that means gotta update all the balances and recalculate them. To do this we're going to have to break down the workflow called refresh account balances by date. So refresh account balances by date. And this workflow takes three inputs. It takes an account, it takes a date, it takes a queue item. That's all it needs to do its job. And as an added precaution, because this process may take longer depending on the number of transactions that need to be recalculated, we're also going to use a field in the account table called calculating balances. We're going to use it as a block so that no other process is going to be able to make changes to that, to the balances of that account for that user. What this does is it says.
Accounts calculating balances is null. So it's not calculating, nobody else is calculating balances for it. Then go off and do the work. Trigger calculate balances. This is a custom event that actually is going to do the job. Otherwise if it is marked as yes, then what I want you to do is just wait and try again. In a little while, schedule yourself to read again for 10 minutes down the road, for 15 minutes down the road, for two days down the road. Whatever you decide, however you want to do that. In this case I have it set up with an option set but not important here. But what I'm doing here is I'm saying if it's busy doing it, somebody else is doing this, then I'll wait, do it again. And however, if it wasn't busy before then I'm just going to mark it as busy now so that nobody else will be able to step in here with this account until I'm finished. That is the first level of this process is Just to see a fun. If it's time to start and if it's time to start, then it's going to trigger Calculate Balances. So this is another custom event, Calculate Balances. And this is where all the work actually starts, really digging and getting going. Let's see how this workflow actually works.
First, it triggers another custom event called Calculate Refresh Transactions. Why am I going to do this? I want to do a search one time and be able to use it throughout this whole workflow without having to repeat it. Why? First of all, because I'm going to save time and money because I don't have to pay bubble to do that search multiple times. And also if I need to change that search, I only have to change it in one place. I don't have to go change it in three or four different places. So it's good practice to do this. So how do I do that? Another one of my little small custom events called Calculate Refresh Transactions. So let's just look and see what it does. This is another really simple custom event that takes an account and a date and it returns a list of transactions and it also returns a list of account balances that are affected. So what it does first it returns a search for transactions, all of whom the date is the same or later than the date that we're starting with. For this account and this user, I'm going to order them by date and I'm just going to return that list of transactions and account balances. I'm going to do something really similar as well. I'm just going to return the list of account balances for this account and this date probably here should put the user in just to be consistent all over the place. So let's do created by is equal to current user. So this first step of calculate balances here all I did was do the searches, find the list of transactions and the list of accounts that are going to be implicated. Step two, I am going to take all of those transactions and use a make changes to a list. I'm going to take the return of those transactions that I in that search and I'm just going to say mark them all as balance adjusted. No. Okay. So that's just something I do internally because I want to keep track of. If I have to go back and debug, I want to see exactly which ones got done and which ones didn't. It's just a logging function. And then I'm going to delete all of the account balances that have been affected. Why? Because I'm going to create them new, so I'm just going to delete them all. And then what I'm going to do is I'm going to schedule my last that we're going to breakdown here, which is the one that is actually going to now take the list of transactions for this queue item and I'm going to wait a couple of seconds or a little bit so that these other processes can finish and I'm going to start this workflow that actually is going to recalculate and refresh the. The transactions balance. So this is the last workflow that I need to walk you through. It's called Refresh Transactions Balance and it has four steps. First step is going to use the custom event that we already went through, which is called Adjust balance. Look at the definition of this backend workflow. It takes a list of transactions and it takes a queue item. There's only one queue item and a list of transactions. Why? Because this is going to be a recursive workflow is going to go one by one through this list and it's going to adjust the balances one by one in order so that I know that they all get done in the right order. So the first thing I'm going to do is I'm going to use that custom event that we already created because it's the same functionality, and I'm going to pass it the account of the first transaction in my list, the amount and the date. Okay. And it's going to do what it already did. I'm not going to explain it again because you've already seen how that works. Now the next thing I'm going to do is I am going to schedule. This is the recursive loop. I'm going to schedule this same workflow to execute for the list that we had minus the first one, because we just processed the first one, same queue item. And I'm going to give it a little bit of a delay. So I'll let it do its little stuff there if there are more of them to be done. So I'm looking at. I'm taking the list minus the item of the one that we just processed. And if there's still more than zero in the list, then I have to call myself and do it again. So that is the condition that will make sure that when we get to zero, it won't keep looping. Otherwise you will pay a fortune to bubble and your recursive workflow will never end. And that's just shake. That's the recursive loop that says okay, I've adjusted the balance now schedule for the next one. However if it is zero, there aren't any more. Then what I want to do is go to the first item, take its account and I'm going to mark calculating balances as null because now we finished and I am also going to modify the queue also same conditional here. If there's no more left, I'm going to mark the queue item as complete and I mark the date and time that queue item was completed. And with that we have processed all of those transactions. Okay, one by one. All done. But if you need to go back, if you need to pause, go back, look at it carefully. If you have any questions, feel free to leave me comments below or reach out to us@ratio.dev in this video we've gone over the complete process for maintaining accurate running balances per all the accounts that have transactions, but we've also learned a lot more. I think we've built a backend queue, which is pretty nifty. It could come in really handy a lot of times. We've built a recursive backend workflow, which we just saw, which is a really fundamental thing for any bubble developer to understand how to do. We've learned a ton about custom events and we've also learned a lot about database triggers. So I really hope that you've enjoyed this video, that you've gotten a lot out of it, and see you on the next video.
More from Dennis

Is Google Killing Websites? The Future of Search, SEO & Web Design After Google I/O

Something we're still looking forward to in Bubble: richer design experiences! #bubble #nocode #ai

Big mistake companies are making right now: firing employees instead of empowering them. #ai







