ERC-1973: Scalable Rewards


Metadata
Status: StagnantStandards Track: ERCCreated: 2019-04-01
Authors
Lee Raj (@lerajk), Qin Jian (@qinjian)

Simple Summary


A mintable token rewards interface that mints 'n' tokens per block which are distributed equally among the 'm' participants in the DAPP's ecosystem.

Abstract


The mintable token rewards interface allows DApps to build a token economy where token rewards are distributed equally among the active participants. The tokens are minted based on per block basis that are configurable (E.g. 10.2356 tokens per block, 0.1 token per block, 1350 tokens per block) and the mint function can be initiated by any active participant. The token rewards distributed to each participant is dependent on the number of participants in the network. At the beginning, when the network has low volume, the tokens rewards per participant is high but as the network scales the token rewards decreases dynamically.

Motivation


Distributing tokens through a push system to a large amount of participants fails due to block gas limit. As the number of participants in the network grow to tens of thousands, keeping track of the iterable registry of participants and their corresponding rewards in a push system becomes unmanagable. E.g. Looping through 5000 addresses to distribute 0.0000001 reward tokens is highly inefficient. Furthermore, the gas fees in these transactions are high and needs to be undertaken by the DApp developer or the respective company, leading to centralization concerns.

A pull system is required to keep the application completely decentralized and to avoid the block gas limit problem. However, no standard solution has been proposed to distribute scalable rewards to tens of thousands participants with a pull system. This is what we propose with this EIP through concepts like TPP, round mask, participant mask.

Specification


Definitions

token amount per participant in the ecosytem or TPP (token per participant): TPP = (token amount to mint / total active participants)

roundMask: the cumulative snapshot of TPP over time for the token contract. E.g. transactionOne = 10 tokens are minted with 100 available participants (TPP = 10 / 100) , transactionTwo = 12 tokens are minted with 95 participants (TPP = 12 / 95 )

roundMask = (10/100) + (12/95)

participantMask: is used to keep track of a msg.sender (participant) rewards over time. When a msg.sender joins or leaves the ecosystem, the player mask is updated

participantMask = previous roundMask OR (current roundMask - TPP)

rewards for msg.sender: roundMask - participantMask

E.g. Let's assume a total of 6 transactions (smart contract triggers or functions calls) are in place with 10 existing participants (denominator) and 20 tokens (numerator) are minted per transaction. At 2nd transaction, the 11th participant joins the network and exits before 5th transaction, the 11th participant's balance is as follows:


Total tokens released in 6 transactions = 60 tokens

As the participant joins at t2 and leaves before t5, the participant deserves the rewards between t2 and t4. When the participant joins at t2, the 'participantMask = (20/10)', when the participant leaves before t5, the cumulative deserved reward tokens are :

rewards for msg.sender: [t4 roundMask = (20/10) + (20/11)+ (20/11) + (20/11)] - [participantMask = (20/10)] = [rewards = (20/11)+ (20/11) + (20/11)]

When the same participant joins the ecosystem at a later point (t27 or t35), a new 'participantMask' is given that is used to calculate the new deserved reward tokens when the participant exits. This process continues dynamically for each participant.

tokensPerBlock: the amount of tokens that will be released per block

blockFreezeInterval: the number of blocks that need to pass until the next mint. E.g. if set to 50 and 'n' tokens were minted at block 'b', the next 'n' tokens won't be minted until 'b + 50' blocks have passed

lastMintedBlockNumber: the block number on which last 'n' tokens were minted

totalParticipants : the total number of participants in the DApp network

tokencontractAddress : the contract address to which tokens will be minted, default is address(this)


Rationale


Currently, there is no standard for a scalable reward distribution mechanism. In order to create a sustainable cryptoeconomic environment within DAPPs, incentives play a large role. However, without a scalable way to distribute rewards to tens of thousands of participants, most DAPPs lack a good incentive structure. The ones with a sustainable cryptoeconomic environment depend heavily on centralized servers or a group of selective nodes to trigger the smart contracts. But, in order to keep an application truly decentralized, the reward distribution mechanism must depend on the active participants itself and scale as the number of participants grow. This is what this EIP intends to accomplish.

Backwards Compatibility


Not Applicable.

Test Cases


WIP, will be added.

Implementation


WIP, a proper implementation will be added later.A sample example is below:

etherscan rewards contract : https://ropsten.etherscan.io/address/0x8b0abfc541ab7558857816a67e186221adf887bc#tokentxns

Step 1 : deploy Rewards contract with the following parameters_tokensPerBlock = 1e18, _blockFreezeInterval = 1

Step 2 : add Alice(0x123) and Bob(0x456) as minters, addMinters(address _minter)

Step 3 : call trigger() from Alice / Bob's account. 65 blocks are passed, hence 65 SIM tokens are minted. The RM is 32500000000000000000

Step 4 : Alice withdraws and receives 32.5 SIM tokens (65 tokens / 2 participants) and her PM = 32500000000000000000

Step 5 : add Satoshi(0x321) and Vitalik(0x654) as minters, addMinters(address _minter)

Step 6 : call trigger() from Alice / Bob's / Satoshi / Vitalik account. 101 blocks are passed, hence 101 SIM tokens are minted. The RM is 57750000000000000000

Step 7 : Alice withdraws and receives 25.25 SIM tokens (101 tokens / 4 participants) and her PM = 57750000000000000000

Step 8 : Bob withdraws and receives 57.75 SIM tokens ((65 tokens / 2 participants) + (101 tokens / 4 participants)). Bob's PM = 57750000000000000000

Copyright


Copyright and related rights waived via CC0.

References


  1. Scalable Reward Distribution on the Ethereum Blockchain by Bogdan Batog, Lucian Boca and Nick Johnson

  2. Fomo3d DApp, https://fomo3d.hostedwiki.co/