Transferring balances between accounts is hard. If you have any sort of sharding, all of a sudden you don't get transaction safety in the transfer. You can have sharding for many reasons, such as different vendors, different locations, different releases and pure performance.<p>So, you transfer and hope for the best, typically everything will be fine.<p>Then you add an asynchronous job to go over the logs and reconcile the results - flagging fraud.<p>There are two ways of processing transactions. You can remove the money first and then add it to the new account. That will tend to show up as "lost" money when the customer sees a problem. Not really a good thing if you're a service business (vs a bank).<p>The other way to go is add the money first and then remove it. That will allow money to be created (as in this case), but won't result in customers seeing money disappear.<p>Finally, there may be a problem where they are reading from a cache to perform the transfer, and the read-copy is a little stale. Again, this would tend towards giving customer's money.