Since we do not have a formal submission process for AIP (Astar Improvement Proposals), I will not put a number in the title. But we should consider making a dedicated category called 'Astar Improvement Proposals
Abstract
According to the dApps Staking v3 specification, the core idea is to allow multiple on-chain criteria to be considered when adjusting the reward tier for dApps. The intention is to create a reward system that is fairly evaluated and prevents freeloaders from appearing.
I propose a metric (that may be one of many other metrics) that can add to the ‘fairness’ of dApp performance evaluation based on the number of new stakers and the staked amount for a given era.
With this metric, we can evaluate and reward dApps based on the community staking activities it is getting and prioritize the rewards for projects that can engage their communities with the network. Astar protocol must take into account the number of new stakers, and the number of stakes and formulate them to output a reward score that is evaluated for the reward tier for a given dApp. With this system, dApps must increase the number of new stakers to maintain a high reward tier.
Motivation
One of the major issues with dApps Staking is that it needs a way to disincentivize freeloaders while not making the reward pool a zero-sum game. dApps Staking v3 allows us to add various on-chain metrics to evaluate this. However, understanding which metrics to track that realistically reflect rewarding ‘high-performance’ dApps was a challenging task. Furthermore, due to the computation limit during a state transition, we cannot track data that scales indefinitely or require off-chain workers (for example, tracking gas consumption or transaction count).
Instead, we should move away from direct measurements and think about how we define a ‘high-performance’ dApp from the very beginning. I came up with this metric through the following thought process:
- What do we want? → to reward high-performing ‘good’ projects
- What is a good project? → a project that provides value to its users
- How do we check that? → a project with a big and thriving community
- How do we check that? → a project with a lot of staking activities
- How do we check that? → a project with a big and thriving community
- What is a good project? → a project that provides value to its users
Here, I take the final metric and rephrase my original question as the following statement:
- We reward the projects on Astar Network based on their staking activities.
In other words, for projects to maintain or gain a high reward tier for their project (which leads to more rewards), they must encourage their community or increase the community size to attract more stakers. This means projects that can closely integrate the dApps Staking function as part of their business logic (ex: staker incentives from the dApp) or a team with a great marketing strategy to encourage more stakes will have a higher chance of accumulating more rewards.
Technical Details
In this section, I will outline the high-level concept using pseudocode so the underlining logic gets across while the implementation is flexible as possible, regardless of the architecture. Also, note that I prioritize readability over functionality (and scalability).
For this system to work, the module must define three constant values: the staker_weight
, stake_weight
, and the evaluation_period_eras
. I will plug in a random value that makes sense at a glance. But the actual parameters must be carefully evaluated.
let staker_weight = 0.9
let stake_weight = 0.1
let evaluation_period_eras = 3
The module must keep track of the number of newly added stakers and the staked amount for each contract in the tier list during the number since the last time it checked. The check (evaluation) will run every era defined in evaluation_period_eras
.
In other words, the module will keep a vector with the length of evaluation_period_eras
for each dApp in the tiers with the newly added stakers and the staked amount. Note that we should also count negative integers. The number type should be something like i128
, not u128
(there is a potential exploit when we use i128
over u128
since the overflow point differs from each other. But these are implementation details that can be solved later).
The following is a simplified version of what the module will be tracking during the specified era.
// For dApp A
let new_stakers_e1 = 18
let new_stakes_e1 = 540000000000000
let new_stakers_e2 = -4
let new_stakes_e2 = -356000000000
let new_stakers_e3 = 2
let new_stakes_e3 = 432500000000000000
In this example, the evaluation function will run at the end of the third era (before the start of the fourth era).
During the evaluation, the module will calculate a contract’s staking performance by adding the number of all stakers and staked during the evaluation period multiplied by each weight.
let total_new_stakers = new_stakers_e1 + new_stakers_e2 + new_stakers_e3
let total_new_stakes = new_stakes_e1 + new_stakes_e2 + new_stakes_e3
let reward_score = staker_weight * total_new_stakers + stake_weight * total_new_stakes
The dApps Staking reward tier list will be reordered based on the final reward score at the end of each evaluation.
Rational
The main components of this system are the weights, evaluation period, and reward score function.
I introduced the evaluation_period_eras
here because we want to check only some of the staking history and make the system scalable. But this value can be made dynamic (or removed completely) by introducing another constant called the era_activity_threshold
, which defines the minimum number of stakers we expect for a given era. If an era does not satisfy the threshold, we delay the evaluation period to the next era. However, this will only make sense if we assume there will be new stakers, and we can only solve the freeloader issue if all projects become tier two in the case of zero staking activities. I will leave it to the forum to discuss which option is better.
For the weights, we add the staker_weight
and the stake_weight
to ensure that even if a project gets a lot of ASTR stakes, if the number of accounts engaged with the project doesn’t increase, we do not consider it to be ‘performing well.’ So the staker_weight
must be sufficiently higher than the stake_weight
for this to be true. In my example, the 0.9
versus 0.1
weight will barely make any difference when we calculate the new_stakes
as a token unit, while the new_stakers
are based on the number of accounts. So this flaw must be addressed during the implementation phase. But I hope my intention was clear.
Finally, the reward_score
is the expected output that will directly affect the reward tier for a dApp. I do not expect the formula to be complicated, but it should be able to evaluate the dApp’s reward tier based on the staker engagement.
Considerations
Exploitation By Bots
What happens if a whale constantly uses bots for staking on a dApp to get more rewards?
This is easily possible in a permissionless system if the account holds any tokens. However, I do not see this as an issue. It’s a good thing if people try to exploit this system. Because we are tracking the delta of stakers and staked tokens, the activity can have a negative score. If a whale decides to pull out their staked tokens and re-stake them, it will have a minimum effect on the evaluation because the negative stake is much bigger than the newly added stakers. To have a high score without penalty, the whale must buy more ASTR tokens and stake them through a bot.
It’s also true that using bots to distribute the stakes will optimize the reward score compared to staking all at once. However, using bots means the staker will spend more gas costs for the same operation. This is counted as part of the network activity growth, and the gas will be redistributed to the network. In other words, using bots will be a net positive for the overall network regarding token growth as the number of chain activities, and TVL will increase.
Lack of Staking Activity
What happens if there are no new stakers in the network for the evaluation period?
This question boils downs to this, should we reduce the tiers for all dApps, or not change the tiers?
I would prefer the former to encourage the network to gain more support and reduce our network inflation based on the TVL (or the lack of it). But it is up to the forum to discuss what would be the better output.
Governance Implications
As noted in my previous post about Astar Governance, Astar will not use ASTR tokens for voting. Instead, issue a virtual govASTR token based on the dApps Staking rewards that are non-transferrable and burnable after a certain period. Having this system alongside the delta rewarding scheme means that the voting power of a dApp will decrease based on its staking activities.
Although this isn’t a problem for dApp project teams, if dApp decides to redistribute its voting power to a delegate or its community (stakers), this system may act as a negative factor that punishes the voters and community members for not doing anything.
To counteract this, I propose that the govASTR token distribution will use the vanilla reward calculation scheme (i.e., dApps Staking v2) distributed based on the total number of staked ASTR tokens.
An individual or a community’s voting power will not be affected by the staking activities as long as it has a lot of staked ASTR tokens to its project.