@bananapus/distributor-v6 0.0.45 → 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +11 -1
- package/package.json +5 -5
- package/src/JBDistributor.sol +7 -2
- package/src/interfaces/IJBDistributor.sol +2 -1
package/README.md
CHANGED
|
@@ -75,7 +75,9 @@ This repo does not explain why an allocation exists. It only defines how funded
|
|
|
75
75
|
NFT's tier
|
|
76
76
|
- `recycleExpiredRewards` is permissionless; it recycles the expired round's unmaterialized remainder while preserving
|
|
77
77
|
amounts that already started vesting
|
|
78
|
-
- eligible expired and forfeited rewards stay in distributor inventory and are recycled into the current reward round
|
|
78
|
+
- eligible expired and forfeited rewards stay in distributor inventory and are recycled into the current reward round.
|
|
79
|
+
A reward round never recycles into itself; if the requested round is still current, the call is a no-op, including
|
|
80
|
+
for zero-stake rounds
|
|
79
81
|
- revnet loan-backed vesting is opt-in at deployment; the reward token must be a REVOwner-owned revnet token, the
|
|
80
82
|
distributor keeps the loan NFT, and repayment restores the original vesting schedule instead of releasing all
|
|
81
83
|
collateral immediately
|
|
@@ -95,6 +97,12 @@ This repo does not explain why an allocation exists. It only defines how funded
|
|
|
95
97
|
`getPastTotalTierActiveVotes` denominator, then cap each numerator with `getPastAccountTierActiveVotes`; this
|
|
96
98
|
requires `@bananapus/721-hook-v6 >= 0.0.73` for the active-vote checkpoints API
|
|
97
99
|
- snapshot timing is part of the trusted surface
|
|
100
|
+
- `poke()`-style keeper or funding flows should be treated as snapshot policy decisions: calling them at a different
|
|
101
|
+
block can change which historical votes or NFTs share a funded round
|
|
102
|
+
- 721 claim helpers should preflight the holder, tier set, checkpoint block, and available distributor inventory before
|
|
103
|
+
batching claims; ownership at the time of submission is not enough if the funded round used an older snapshot
|
|
104
|
+
- direct token or native-token balances at a distributor are unaccounted inventory until an explicit funding or recycle
|
|
105
|
+
path assigns them to a reward round
|
|
98
106
|
- this repo settles distributions, but it does not prove the upstream entitlement math was correct
|
|
99
107
|
|
|
100
108
|
## Where state lives
|
|
@@ -153,6 +161,8 @@ script/
|
|
|
153
161
|
- teams should review claim timing and snapshot assumptions with the same care they review the payout source
|
|
154
162
|
- token distributors require hooks that expose `IJBActiveVotes`; expiring token rounds recycle any unmaterialized
|
|
155
163
|
remainder after the deadline
|
|
164
|
+
- payout-split funding always enters the default reward group; tier-scoped rewards need explicit funding and matching
|
|
165
|
+
tier-scoped claim parameters
|
|
156
166
|
|
|
157
167
|
## For AI agents
|
|
158
168
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@bananapus/distributor-v6",
|
|
3
|
-
"version": "0.0
|
|
3
|
+
"version": "1.0.0",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -24,12 +24,12 @@
|
|
|
24
24
|
"deploy:testnets": "source ./.env && npx sphinx propose ./script/Deploy.s.sol --networks testnets"
|
|
25
25
|
},
|
|
26
26
|
"dependencies": {
|
|
27
|
-
"@bananapus/721-hook-v6": "^0.0
|
|
28
|
-
"@bananapus/core-v6": "^0.0
|
|
29
|
-
"@bananapus/permission-ids-v6": "^0.0
|
|
27
|
+
"@bananapus/721-hook-v6": "^1.0.0",
|
|
28
|
+
"@bananapus/core-v6": "^1.0.0",
|
|
29
|
+
"@bananapus/permission-ids-v6": "^1.0.0",
|
|
30
30
|
"@openzeppelin/contracts": "5.6.1",
|
|
31
31
|
"@prb/math": "4.1.2",
|
|
32
|
-
"@rev-net/core-v6": "^0.0
|
|
32
|
+
"@rev-net/core-v6": "^1.0.0"
|
|
33
33
|
},
|
|
34
34
|
"devDependencies": {
|
|
35
35
|
"@sphinx-labs/plugins": "0.33.3"
|
package/src/JBDistributor.sol
CHANGED
|
@@ -305,7 +305,8 @@ abstract contract JBDistributor is IJBDistributor {
|
|
|
305
305
|
}
|
|
306
306
|
|
|
307
307
|
/// @notice Recycle unclaimed rewards from expired reward rounds into the current reward round.
|
|
308
|
-
/// @dev Recycling is permissionless; any keeper or frontend can sweep an
|
|
308
|
+
/// @dev Recycling is permissionless; any keeper or frontend can sweep an eligible prior round. Passing the current
|
|
309
|
+
/// reward round is a no-op, even when its snapshot stake is zero.
|
|
309
310
|
/// @param hook The hook whose expired rewards should be recycled.
|
|
310
311
|
/// @param token The reward token to recycle.
|
|
311
312
|
/// @param rounds The reward rounds to recycle.
|
|
@@ -1185,6 +1186,11 @@ abstract contract JBDistributor is IJBDistributor {
|
|
|
1185
1186
|
internal
|
|
1186
1187
|
returns (uint256 recycleAmount)
|
|
1187
1188
|
{
|
|
1189
|
+
// Never recycle a round into itself. This keeps raw round accounting stable for zero-stake current rounds; the
|
|
1190
|
+
// same inventory can be swept once a later round is current.
|
|
1191
|
+
uint256 recycledToRound = currentRound();
|
|
1192
|
+
if (round == recycledToRound) return 0;
|
|
1193
|
+
|
|
1188
1194
|
// Load the reward round once so expiry, claimed amount, and funded amount stay in sync.
|
|
1189
1195
|
JBRewardRoundData storage rewardRound = rewardRoundOf[hook][groupId][token][round];
|
|
1190
1196
|
|
|
@@ -1204,7 +1210,6 @@ abstract contract JBDistributor is IJBDistributor {
|
|
|
1204
1210
|
rewardRound.claimedAmount = rewardRound.amount;
|
|
1205
1211
|
|
|
1206
1212
|
// Keep the inventory in the distributor and give the current staker set a new claimable round.
|
|
1207
|
-
uint256 recycledToRound = currentRound();
|
|
1208
1213
|
_recordRewardRound({hook: hook, groupId: groupId, token: token, amount: recycleAmount});
|
|
1209
1214
|
|
|
1210
1215
|
// Surface the permissionless recycle for off-chain accounting.
|
|
@@ -301,7 +301,8 @@ interface IJBDistributor {
|
|
|
301
301
|
/// @notice Record the snapshot block for the current round. Callable by anyone (keepers, frontends).
|
|
302
302
|
function poke() external;
|
|
303
303
|
|
|
304
|
-
/// @notice Recycle unclaimed rewards from
|
|
304
|
+
/// @notice Recycle unclaimed rewards from eligible prior default-group reward rounds into the current reward round.
|
|
305
|
+
/// @dev Passing the current round is a no-op, including for zero-stake rounds.
|
|
305
306
|
/// @param hook The hook whose expired reward rounds should be recycled.
|
|
306
307
|
/// @param token The reward token to recycle.
|
|
307
308
|
/// @param rounds The reward rounds to recycle.
|