I am trying to implement a simple lottery as a pet project and to get into solidity coding.
I am running into an issue and I wonder what is the best way to solve it. Basically during a timeframe of a draw x participants take part. X could potentially be very big, lets say 10k. At the end of the draw winning numbers are being generated and I need to go through all participations and check whether they have won and how much. Both would be public methods accessible only to the owner.
Problem What can I do to not run into out of gas issues, especially hitting the maximum gas per block limit when the number of participants gets too large?
Now I see two ways to solve this:
have a method that returns the amount of participants
have a central service that paginates through that amount by lets say 50 each and calls a "determine winners" method
have a method that then calls the payouts
do the same paginated method calling for the payouts
have a determineWinners method that iterates through lets 50 of the total participants to check for winning numbers
when done and there are still unchecked participants left, store the last iteration variable (eg 50 or 100 aso) and create an event that lets a central service know, to call that method again until done
do the same for payouts
In general I don't like the heavy dependency on the centralised control authority of the contract. Also both methods would be very slow. Determining winners out of a pool of 10k in steps of 50 and a block time of 20 sec would already take more than an hour. 200k users would not work anymore if I run the lottery on a daily basis.
Is there some sort of best practice on how this can be done?
Do the methods presented make sense? Which one is preferable?
Are there other ways?
Thanks a lot for your help. Gordon