@boostxyz/sdk 2.1.2 → 2.2.1
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/dist/Actions/Action.cjs +1 -1
- package/dist/Actions/Action.cjs.map +1 -1
- package/dist/Actions/Action.d.ts +2 -1
- package/dist/Actions/Action.d.ts.map +1 -1
- package/dist/Actions/Action.js +14 -13
- package/dist/Actions/Action.js.map +1 -1
- package/dist/Actions/EventAction.cjs +1 -1
- package/dist/Actions/EventAction.cjs.map +1 -1
- package/dist/Actions/EventAction.d.ts +219 -0
- package/dist/Actions/EventAction.d.ts.map +1 -1
- package/dist/Actions/EventAction.js +39 -39
- package/dist/Actions/EventAction.js.map +1 -1
- package/dist/AllowLists/AllowList.cjs +1 -1
- package/dist/AllowLists/AllowList.cjs.map +1 -1
- package/dist/AllowLists/AllowList.d.ts +2 -1
- package/dist/AllowLists/AllowList.d.ts.map +1 -1
- package/dist/AllowLists/AllowList.js +18 -17
- package/dist/AllowLists/AllowList.js.map +1 -1
- package/dist/AllowLists/SimpleAllowList.cjs +1 -1
- package/dist/AllowLists/SimpleAllowList.js +9 -9
- package/dist/AllowLists/SimpleDenyList.cjs +1 -1
- package/dist/AllowLists/SimpleDenyList.js +2 -2
- package/dist/Auth/PassthroughAuth.cjs +1 -1
- package/dist/Auth/PassthroughAuth.js +1 -1
- package/dist/BoostCore.cjs +2 -2
- package/dist/BoostCore.cjs.map +1 -1
- package/dist/BoostCore.d.ts +33 -0
- package/dist/BoostCore.d.ts.map +1 -1
- package/dist/BoostCore.js +98 -81
- package/dist/BoostCore.js.map +1 -1
- package/dist/BoostRegistry.cjs +1 -1
- package/dist/BoostRegistry.js +12 -12
- package/dist/{Budget-CUIFf1Br.js → Budget-2Zb3Mb-8.js} +40 -39
- package/dist/{Budget-CUIFf1Br.js.map → Budget-2Zb3Mb-8.js.map} +1 -1
- package/dist/{Budget-cI30CIMN.cjs → Budget-2xKEvkbL.cjs} +2 -2
- package/dist/{Budget-cI30CIMN.cjs.map → Budget-2xKEvkbL.cjs.map} +1 -1
- package/dist/Budgets/Budget.cjs +1 -1
- package/dist/Budgets/Budget.d.ts +2 -1
- package/dist/Budgets/Budget.d.ts.map +1 -1
- package/dist/Budgets/Budget.js +3 -3
- package/dist/Budgets/ManagedBudget.cjs +1 -1
- package/dist/Budgets/ManagedBudget.js +33 -33
- package/dist/Deployable/DeployableTarget.cjs +1 -1
- package/dist/Deployable/DeployableTarget.js +1 -1
- package/dist/Deployable/DeployableTargetWithRBAC.cjs +1 -1
- package/dist/Deployable/DeployableTargetWithRBAC.cjs.map +1 -1
- package/dist/Deployable/DeployableTargetWithRBAC.d.ts +158 -0
- package/dist/Deployable/DeployableTargetWithRBAC.d.ts.map +1 -1
- package/dist/Deployable/DeployableTargetWithRBAC.js +268 -31
- package/dist/Deployable/DeployableTargetWithRBAC.js.map +1 -1
- package/dist/Incentive-CfIjdL4T.cjs +2 -0
- package/dist/Incentive-CfIjdL4T.cjs.map +1 -0
- package/dist/Incentive-DNwTyG5Z.js +393 -0
- package/dist/Incentive-DNwTyG5Z.js.map +1 -0
- package/dist/Incentives/AllowListIncentive.cjs +1 -1
- package/dist/Incentives/AllowListIncentive.cjs.map +1 -1
- package/dist/Incentives/AllowListIncentive.js +28 -28
- package/dist/Incentives/AllowListIncentive.js.map +1 -1
- package/dist/Incentives/CGDAIncentive.cjs +1 -1
- package/dist/Incentives/CGDAIncentive.cjs.map +1 -1
- package/dist/Incentives/CGDAIncentive.d.ts +30 -0
- package/dist/Incentives/CGDAIncentive.d.ts.map +1 -1
- package/dist/Incentives/CGDAIncentive.js +25 -25
- package/dist/Incentives/CGDAIncentive.js.map +1 -1
- package/dist/Incentives/ERC1155Incentive.d.ts +25 -0
- package/dist/Incentives/ERC1155Incentive.d.ts.map +1 -1
- package/dist/Incentives/ERC20Incentive.cjs +1 -1
- package/dist/Incentives/ERC20Incentive.cjs.map +1 -1
- package/dist/Incentives/ERC20Incentive.d.ts +30 -0
- package/dist/Incentives/ERC20Incentive.d.ts.map +1 -1
- package/dist/Incentives/ERC20Incentive.js +42 -42
- package/dist/Incentives/ERC20Incentive.js.map +1 -1
- package/dist/Incentives/ERC20PeggedIncentive.d.ts +905 -0
- package/dist/Incentives/ERC20PeggedIncentive.d.ts.map +1 -0
- package/dist/Incentives/ERC20VariableCriteriaIncentive.cjs +1 -1
- package/dist/Incentives/ERC20VariableCriteriaIncentive.cjs.map +1 -1
- package/dist/Incentives/ERC20VariableCriteriaIncentive.d.ts +67 -0
- package/dist/Incentives/ERC20VariableCriteriaIncentive.d.ts.map +1 -1
- package/dist/Incentives/ERC20VariableCriteriaIncentive.js +31 -31
- package/dist/Incentives/ERC20VariableCriteriaIncentive.js.map +1 -1
- package/dist/Incentives/ERC20VariableIncentive.cjs +1 -1
- package/dist/Incentives/ERC20VariableIncentive.cjs.map +1 -1
- package/dist/Incentives/ERC20VariableIncentive.d.ts +20 -0
- package/dist/Incentives/ERC20VariableIncentive.d.ts.map +1 -1
- package/dist/Incentives/ERC20VariableIncentive.js +18 -18
- package/dist/Incentives/ERC20VariableIncentive.js.map +1 -1
- package/dist/Incentives/Incentive.cjs +1 -1
- package/dist/Incentives/Incentive.cjs.map +1 -1
- package/dist/Incentives/Incentive.d.ts +26 -4
- package/dist/Incentives/Incentive.d.ts.map +1 -1
- package/dist/Incentives/Incentive.js +20 -40
- package/dist/Incentives/Incentive.js.map +1 -1
- package/dist/Incentives/PointsIncentive.cjs +1 -1
- package/dist/Incentives/PointsIncentive.cjs.map +1 -1
- package/dist/Incentives/PointsIncentive.d.ts +25 -0
- package/dist/Incentives/PointsIncentive.d.ts.map +1 -1
- package/dist/Incentives/PointsIncentive.js +29 -29
- package/dist/Incentives/PointsIncentive.js.map +1 -1
- package/dist/{SimpleDenyList-Ds0CQ4uR.cjs → SimpleDenyList-BQ0GqQfC.cjs} +2 -2
- package/dist/{SimpleDenyList-Ds0CQ4uR.cjs.map → SimpleDenyList-BQ0GqQfC.cjs.map} +1 -1
- package/dist/{SimpleDenyList-CXruWOyu.js → SimpleDenyList-D49GF3NX.js} +11 -11
- package/dist/{SimpleDenyList-CXruWOyu.js.map → SimpleDenyList-D49GF3NX.js.map} +1 -1
- package/dist/Validators/LimitedSignerValidator.cjs +1 -1
- package/dist/Validators/LimitedSignerValidator.d.ts +10 -0
- package/dist/Validators/LimitedSignerValidator.d.ts.map +1 -1
- package/dist/Validators/LimitedSignerValidator.js +15 -15
- package/dist/Validators/SignerValidator.cjs +1 -1
- package/dist/Validators/SignerValidator.cjs.map +1 -1
- package/dist/Validators/SignerValidator.d.ts +10 -0
- package/dist/Validators/SignerValidator.d.ts.map +1 -1
- package/dist/Validators/SignerValidator.js +8 -8
- package/dist/Validators/SignerValidator.js.map +1 -1
- package/dist/Validators/Validator.cjs +1 -1
- package/dist/Validators/Validator.cjs.map +1 -1
- package/dist/Validators/Validator.d.ts +2 -1
- package/dist/Validators/Validator.d.ts.map +1 -1
- package/dist/Validators/Validator.js +20 -19
- package/dist/Validators/Validator.js.map +1 -1
- package/dist/{componentInterfaces-dakxtQHf.js → componentInterfaces-C4uAYjSo.js} +12 -12
- package/dist/componentInterfaces-C4uAYjSo.js.map +1 -0
- package/dist/deployments.json +3 -0
- package/dist/{generated-BTslM7bf.js → generated-B5pVBNb-.js} +1835 -730
- package/dist/generated-B5pVBNb-.js.map +1 -0
- package/dist/generated-D50hBWtr.cjs +3 -0
- package/dist/generated-D50hBWtr.cjs.map +1 -0
- package/dist/index.cjs +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +113 -110
- package/package.json +2 -2
- package/src/Actions/Action.ts +3 -0
- package/src/Actions/EventAction.test.ts +49 -2
- package/src/Actions/EventAction.ts +12 -4
- package/src/AllowLists/AllowList.ts +3 -0
- package/src/BoostCore.ts +27 -5
- package/src/Budgets/Budget.ts +3 -0
- package/src/Deployable/DeployableTargetWithRBAC.test.ts +175 -0
- package/src/Deployable/DeployableTargetWithRBAC.ts +281 -0
- package/src/Incentives/AllowListIncentive.test.ts +48 -0
- package/src/Incentives/AllowListIncentive.ts +1 -1
- package/src/Incentives/CGDAIncentive.test.ts +50 -0
- package/src/Incentives/CGDAIncentive.ts +1 -1
- package/src/Incentives/ERC1155Incentive.ts +1 -1
- package/src/Incentives/ERC20Incentive.test.ts +49 -0
- package/src/Incentives/ERC20Incentive.ts +1 -1
- package/src/Incentives/ERC20PeggedIncentive.ts +507 -0
- package/src/Incentives/ERC20VariableIncentive.test.ts +48 -0
- package/src/Incentives/ERC20VariableIncentive.ts +1 -1
- package/src/Incentives/Incentive.ts +9 -1
- package/src/Incentives/PointsIncentive.test.ts +51 -0
- package/src/Incentives/PointsIncentive.ts +1 -1
- package/src/Validators/Validator.ts +3 -0
- package/src/index.ts +1 -0
- package/dist/componentInterfaces-dakxtQHf.js.map +0 -1
- package/dist/generated-BTslM7bf.js.map +0 -1
- package/dist/generated-DhXxTQ20.cjs +0 -3
- package/dist/generated-DhXxTQ20.cjs.map +0 -1
|
@@ -8,6 +8,11 @@ import {
|
|
|
8
8
|
freshManagedBudget,
|
|
9
9
|
} from '@boostxyz/test/helpers';
|
|
10
10
|
import { Roles } from './DeployableTargetWithRBAC';
|
|
11
|
+
import { createTestClient, http, zeroAddress, publicActions, walletActions } from 'viem';
|
|
12
|
+
import { setupConfig } from '@boostxyz/test/viem';
|
|
13
|
+
import { privateKeyToAccount } from 'viem/accounts';
|
|
14
|
+
import { hardhat } from 'viem/chains';
|
|
15
|
+
import { ManagedBudget } from '../Budgets/ManagedBudget';
|
|
11
16
|
|
|
12
17
|
let fixtures: Fixtures;
|
|
13
18
|
|
|
@@ -100,4 +105,174 @@ describe('RBAC', () => {
|
|
|
100
105
|
expect(await budget.isAuthorized(user)).toBe(false);
|
|
101
106
|
expect(await budget.rolesOf(user)).not.toContain(Roles.MANAGER);
|
|
102
107
|
});
|
|
108
|
+
|
|
109
|
+
test('can transfer ownership', async () => {
|
|
110
|
+
const budget = await loadFixture(freshManagedBudget(defaultOptions, fixtures));
|
|
111
|
+
const oldOwner = accounts[0].account;
|
|
112
|
+
const newOwner = accounts[9].account;
|
|
113
|
+
expect(await budget.owner()).toBe(oldOwner);
|
|
114
|
+
|
|
115
|
+
// Transfer ownership
|
|
116
|
+
await budget.transferOwnership(newOwner);
|
|
117
|
+
|
|
118
|
+
// Verify the new owner
|
|
119
|
+
expect(await budget.owner()).toBe(newOwner);
|
|
120
|
+
});
|
|
121
|
+
|
|
122
|
+
test('can renounce ownership', async () => {
|
|
123
|
+
const budget = await loadFixture(freshManagedBudget(defaultOptions, fixtures));
|
|
124
|
+
const owner = accounts[0].account;
|
|
125
|
+
|
|
126
|
+
// Verify initial owner
|
|
127
|
+
expect(await budget.owner()).toBe(owner);
|
|
128
|
+
|
|
129
|
+
// Renounce ownership
|
|
130
|
+
await budget.renounceOwnership();
|
|
131
|
+
const newOwner = await budget.owner();
|
|
132
|
+
expect(newOwner).toBe(zeroAddress);
|
|
133
|
+
});
|
|
134
|
+
|
|
135
|
+
test('supports two-step ownership handover', async () => {
|
|
136
|
+
const budget = await loadFixture(freshManagedBudget(defaultOptions, fixtures));
|
|
137
|
+
const currentOwner = accounts[0].account;
|
|
138
|
+
const newOwner = accounts[6];
|
|
139
|
+
|
|
140
|
+
const walletClient = createTestClient({
|
|
141
|
+
transport: http('http://127.0.0.1:8545', { retryCount: 0 }),
|
|
142
|
+
chain: hardhat,
|
|
143
|
+
mode: 'hardhat',
|
|
144
|
+
account: privateKeyToAccount(newOwner.key),
|
|
145
|
+
key: newOwner.key,
|
|
146
|
+
})
|
|
147
|
+
.extend(publicActions)
|
|
148
|
+
.extend(walletActions) as any;
|
|
149
|
+
|
|
150
|
+
const newOwnerOptions = {
|
|
151
|
+
account: privateKeyToAccount(newOwner.key),
|
|
152
|
+
config: setupConfig(walletClient)
|
|
153
|
+
};
|
|
154
|
+
|
|
155
|
+
// Create budget instance with different signer
|
|
156
|
+
const sameBudgetDifferentSigner = new ManagedBudget(
|
|
157
|
+
{ config: newOwnerOptions.config, account: newOwnerOptions.account },
|
|
158
|
+
budget.address
|
|
159
|
+
);
|
|
160
|
+
|
|
161
|
+
await sameBudgetDifferentSigner.requestOwnershipHandover();
|
|
162
|
+
|
|
163
|
+
// Verify initial ownership
|
|
164
|
+
expect(await budget.owner()).toBe(currentOwner);
|
|
165
|
+
expect(await sameBudgetDifferentSigner.owner()).toBe(currentOwner);
|
|
166
|
+
|
|
167
|
+
// Complete handover from current owner
|
|
168
|
+
await budget.completeOwnershipHandover(newOwner.account);
|
|
169
|
+
|
|
170
|
+
// Verify ownership has transferred
|
|
171
|
+
expect(await budget.owner()).toBe(newOwner.account);
|
|
172
|
+
expect(await sameBudgetDifferentSigner.owner()).toBe(newOwner.account);
|
|
173
|
+
});
|
|
174
|
+
|
|
175
|
+
test('ownership handover fails if not requested', async () => {
|
|
176
|
+
const budget = await loadFixture(freshManagedBudget(defaultOptions, fixtures));
|
|
177
|
+
const newOwner = accounts[7].account;
|
|
178
|
+
|
|
179
|
+
// Try to complete handover without request
|
|
180
|
+
await expect(
|
|
181
|
+
budget.completeOwnershipHandover(newOwner)
|
|
182
|
+
).rejects.toThrowError('NoHandoverRequest');
|
|
183
|
+
});
|
|
184
|
+
|
|
185
|
+
test('can cancel ownership handover', async () => {
|
|
186
|
+
const budget = await loadFixture(freshManagedBudget(defaultOptions, fixtures));
|
|
187
|
+
const currentOwner = accounts[0].account;
|
|
188
|
+
const newOwner = accounts[6];
|
|
189
|
+
|
|
190
|
+
// Create new options with new owner's account and wallet client
|
|
191
|
+
const walletClient = createTestClient({
|
|
192
|
+
transport: http('http://127.0.0.1:8545', { retryCount: 0 }),
|
|
193
|
+
chain: hardhat,
|
|
194
|
+
mode: 'hardhat',
|
|
195
|
+
account: privateKeyToAccount(newOwner.key),
|
|
196
|
+
key: newOwner.key,
|
|
197
|
+
})
|
|
198
|
+
.extend(publicActions)
|
|
199
|
+
.extend(walletActions) as any;
|
|
200
|
+
|
|
201
|
+
const newOwnerOptions = {
|
|
202
|
+
account: privateKeyToAccount(newOwner.key),
|
|
203
|
+
config: setupConfig(walletClient)
|
|
204
|
+
};
|
|
205
|
+
|
|
206
|
+
// Create budget instance with different signer
|
|
207
|
+
const sameBudgetDifferentSigner = new ManagedBudget(
|
|
208
|
+
{ config: newOwnerOptions.config, account: newOwnerOptions.account },
|
|
209
|
+
budget.address
|
|
210
|
+
);
|
|
211
|
+
|
|
212
|
+
// Request handover from new owner account
|
|
213
|
+
await sameBudgetDifferentSigner.requestOwnershipHandover();
|
|
214
|
+
|
|
215
|
+
// Cancel the handover request
|
|
216
|
+
await sameBudgetDifferentSigner.cancelOwnershipHandover();
|
|
217
|
+
|
|
218
|
+
// Verify handover can't be completed after cancellation
|
|
219
|
+
await expect(
|
|
220
|
+
budget.completeOwnershipHandover(newOwner.account)
|
|
221
|
+
).rejects.toThrowError('NoHandoverRequest');
|
|
222
|
+
|
|
223
|
+
// Verify ownership hasn't changed
|
|
224
|
+
expect(await budget.owner()).toBe(currentOwner);
|
|
225
|
+
});
|
|
226
|
+
|
|
227
|
+
test('can check ownership handover expiry', async () => {
|
|
228
|
+
const budget = await loadFixture(freshManagedBudget(defaultOptions, fixtures));
|
|
229
|
+
const newOwner = accounts[6];
|
|
230
|
+
|
|
231
|
+
const walletClient = createTestClient({
|
|
232
|
+
transport: http('http://127.0.0.1:8545', { retryCount: 0 }),
|
|
233
|
+
chain: hardhat,
|
|
234
|
+
mode: 'hardhat',
|
|
235
|
+
account: privateKeyToAccount(newOwner.key),
|
|
236
|
+
key: newOwner.key,
|
|
237
|
+
})
|
|
238
|
+
.extend(publicActions)
|
|
239
|
+
.extend(walletActions) as any;
|
|
240
|
+
|
|
241
|
+
const newOwnerOptions = {
|
|
242
|
+
account: privateKeyToAccount(newOwner.key),
|
|
243
|
+
config: setupConfig(walletClient)
|
|
244
|
+
};
|
|
245
|
+
|
|
246
|
+
// Create identical budget instance with different signer
|
|
247
|
+
const sameBudgetDifferentSigner = new ManagedBudget(
|
|
248
|
+
{ config: newOwnerOptions.config, account: newOwnerOptions.account },
|
|
249
|
+
budget.address
|
|
250
|
+
);
|
|
251
|
+
|
|
252
|
+
// Check expiry before request (should be 0)
|
|
253
|
+
expect(await budget.ownershipHandoverExpiresAt(newOwner.account)).toBe(0n);
|
|
254
|
+
|
|
255
|
+
// Request handover
|
|
256
|
+
await sameBudgetDifferentSigner.requestOwnershipHandover();
|
|
257
|
+
|
|
258
|
+
// Check expiry after request (should be > 0)
|
|
259
|
+
const expiryTime = await budget.ownershipHandoverExpiresAt(newOwner.account);
|
|
260
|
+
expect(expiryTime).toBeGreaterThan(0n);
|
|
261
|
+
|
|
262
|
+
// Cancel request
|
|
263
|
+
await sameBudgetDifferentSigner.cancelOwnershipHandover();
|
|
264
|
+
|
|
265
|
+
// Check expiry after cancellation (should be 0 again)
|
|
266
|
+
expect(await budget.ownershipHandoverExpiresAt(newOwner.account)).toBe(0n);
|
|
267
|
+
});
|
|
268
|
+
|
|
269
|
+
test('can renounce roles', async () => {
|
|
270
|
+
const budget = await loadFixture(freshManagedBudget(defaultOptions, fixtures));
|
|
271
|
+
const account = accounts[0];
|
|
272
|
+
const user = account.account;
|
|
273
|
+
|
|
274
|
+
expect(await budget.hasAllRoles(user, Roles.ADMIN)).toBe(true);
|
|
275
|
+
await budget.renounceRoles(Roles.ADMIN);
|
|
276
|
+
expect(await budget.hasAllRoles(user, Roles.ADMIN)).toBe(false);
|
|
277
|
+
});
|
|
103
278
|
});
|
|
@@ -1,14 +1,27 @@
|
|
|
1
1
|
import {
|
|
2
2
|
rbacAbi,
|
|
3
|
+
readOwnableRolesOwnershipHandoverExpiresAt,
|
|
3
4
|
readRbacHasAllRoles,
|
|
4
5
|
readRbacHasAnyRole,
|
|
5
6
|
readRbacIsAuthorized,
|
|
6
7
|
readRbacRolesOf,
|
|
8
|
+
simulateOwnableRolesCancelOwnershipHandover,
|
|
9
|
+
simulateOwnableRolesCompleteOwnershipHandover,
|
|
10
|
+
simulateOwnableRolesRenounceOwnership,
|
|
11
|
+
simulateOwnableRolesRenounceRoles,
|
|
12
|
+
simulateOwnableRolesRequestOwnershipHandover,
|
|
13
|
+
simulateOwnableRolesTransferOwnership,
|
|
7
14
|
simulateRbacGrantManyRoles,
|
|
8
15
|
simulateRbacGrantRoles,
|
|
9
16
|
simulateRbacRevokeManyRoles,
|
|
10
17
|
simulateRbacRevokeRoles,
|
|
11
18
|
simulateRbacSetAuthorized,
|
|
19
|
+
writeOwnableRolesCancelOwnershipHandover,
|
|
20
|
+
writeOwnableRolesCompleteOwnershipHandover,
|
|
21
|
+
writeOwnableRolesRenounceOwnership,
|
|
22
|
+
writeOwnableRolesRenounceRoles,
|
|
23
|
+
writeOwnableRolesRequestOwnershipHandover,
|
|
24
|
+
writeOwnableRolesTransferOwnership,
|
|
12
25
|
writeRbacGrantManyRoles,
|
|
13
26
|
writeRbacGrantRoles,
|
|
14
27
|
writeRbacRevokeManyRoles,
|
|
@@ -426,4 +439,272 @@ export class DeployableTargetWithRBAC<
|
|
|
426
439
|
...(params as any),
|
|
427
440
|
});
|
|
428
441
|
}
|
|
442
|
+
|
|
443
|
+
/**
|
|
444
|
+
* Transfer ownership of the contract to a new address
|
|
445
|
+
*
|
|
446
|
+
* @public
|
|
447
|
+
* @async
|
|
448
|
+
* @param {Address} newOwner - The address to transfer ownership to
|
|
449
|
+
* @param {?WriteParams} [params]
|
|
450
|
+
* @returns {Promise<void>}
|
|
451
|
+
*/
|
|
452
|
+
public async transferOwnership(newOwner: Address, params?: WriteParams) {
|
|
453
|
+
return await this.awaitResult(this.transferOwnershipRaw(newOwner, params));
|
|
454
|
+
}
|
|
455
|
+
|
|
456
|
+
/**
|
|
457
|
+
* Transfer ownership of the contract to a new address
|
|
458
|
+
*
|
|
459
|
+
* @public
|
|
460
|
+
* @async
|
|
461
|
+
* @param {Address} newOwner - The address to transfer ownership to
|
|
462
|
+
* @param {?WriteParams} [params]
|
|
463
|
+
* @returns {Promise<{ hash: `0x${string}`; result: void; }>}
|
|
464
|
+
*/
|
|
465
|
+
public async transferOwnershipRaw(newOwner: Address, params?: WriteParams) {
|
|
466
|
+
const { request, result } = await simulateOwnableRolesTransferOwnership(
|
|
467
|
+
this._config,
|
|
468
|
+
{
|
|
469
|
+
address: this.assertValidAddress(),
|
|
470
|
+
args: [newOwner],
|
|
471
|
+
...this.optionallyAttachAccount(),
|
|
472
|
+
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
473
|
+
...(params as any),
|
|
474
|
+
},
|
|
475
|
+
);
|
|
476
|
+
const hash = await writeOwnableRolesTransferOwnership(
|
|
477
|
+
this._config,
|
|
478
|
+
request,
|
|
479
|
+
);
|
|
480
|
+
return { hash, result };
|
|
481
|
+
}
|
|
482
|
+
|
|
483
|
+
/**
|
|
484
|
+
* Renounce ownership of the contract
|
|
485
|
+
*
|
|
486
|
+
* @public
|
|
487
|
+
* @async
|
|
488
|
+
* @param {?WriteParams} [params]
|
|
489
|
+
* @returns {Promise<void>}
|
|
490
|
+
*/
|
|
491
|
+
public async renounceOwnership(params?: WriteParams) {
|
|
492
|
+
return await this.awaitResult(this.renounceOwnershipRaw(params));
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
/**
|
|
496
|
+
* Renounce ownership of the contract
|
|
497
|
+
*
|
|
498
|
+
* @public
|
|
499
|
+
* @async
|
|
500
|
+
* @param {?WriteParams} [params]
|
|
501
|
+
* @returns {Promise<{ hash: `0x${string}`; result: void; }>}
|
|
502
|
+
*/
|
|
503
|
+
public async renounceOwnershipRaw(params?: WriteParams) {
|
|
504
|
+
const { request, result } = await simulateOwnableRolesRenounceOwnership(
|
|
505
|
+
this._config,
|
|
506
|
+
{
|
|
507
|
+
address: this.assertValidAddress(),
|
|
508
|
+
...this.optionallyAttachAccount(),
|
|
509
|
+
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
510
|
+
...(params as any),
|
|
511
|
+
},
|
|
512
|
+
);
|
|
513
|
+
const hash = await writeOwnableRolesRenounceOwnership(
|
|
514
|
+
this._config,
|
|
515
|
+
request,
|
|
516
|
+
);
|
|
517
|
+
return { hash, result };
|
|
518
|
+
}
|
|
519
|
+
|
|
520
|
+
/**
|
|
521
|
+
* Request a two-step ownership handover to the caller
|
|
522
|
+
* The request will automatically expire in 48 hours
|
|
523
|
+
*
|
|
524
|
+
* Note: This is part of a two-step ownership transfer process:
|
|
525
|
+
* 1. New owner calls requestOwnershipHandover()
|
|
526
|
+
* 2. Current owner calls completeOwnershipHandover(newOwner)
|
|
527
|
+
*
|
|
528
|
+
* @public
|
|
529
|
+
* @async
|
|
530
|
+
* @param {?WriteParams} [params]
|
|
531
|
+
* @returns {Promise<void>}
|
|
532
|
+
*/
|
|
533
|
+
public async requestOwnershipHandover(params?: WriteParams) {
|
|
534
|
+
return await this.awaitResult(this.requestOwnershipHandoverRaw(params));
|
|
535
|
+
}
|
|
536
|
+
|
|
537
|
+
/**
|
|
538
|
+
* Request a two-step ownership handover to the caller
|
|
539
|
+
* The request will automatically expire in 48 hours
|
|
540
|
+
*
|
|
541
|
+
* @public
|
|
542
|
+
* @async
|
|
543
|
+
* @param {?WriteParams} [params]
|
|
544
|
+
* @returns {Promise<{ hash: `0x${string}`; result: void; }>}
|
|
545
|
+
*/
|
|
546
|
+
public async requestOwnershipHandoverRaw(params?: WriteParams) {
|
|
547
|
+
const { request, result } =
|
|
548
|
+
await simulateOwnableRolesRequestOwnershipHandover(this._config, {
|
|
549
|
+
address: this.assertValidAddress(),
|
|
550
|
+
...this.optionallyAttachAccount(),
|
|
551
|
+
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
552
|
+
...(params as any),
|
|
553
|
+
});
|
|
554
|
+
const hash = await writeOwnableRolesRequestOwnershipHandover(
|
|
555
|
+
this._config,
|
|
556
|
+
request,
|
|
557
|
+
);
|
|
558
|
+
return { hash, result };
|
|
559
|
+
}
|
|
560
|
+
|
|
561
|
+
/**
|
|
562
|
+
* Complete a pending ownership handover to a new owner
|
|
563
|
+
* Must be called by the current owner after the new owner has requested the handover
|
|
564
|
+
*
|
|
565
|
+
* Note: This is part of a two-step ownership transfer process:
|
|
566
|
+
* 1. New owner calls requestOwnershipHandover()
|
|
567
|
+
* 2. Current owner calls completeOwnershipHandover(newOwner)
|
|
568
|
+
*
|
|
569
|
+
* @public
|
|
570
|
+
* @async
|
|
571
|
+
* @param {Address} pendingOwner - The address that requested the ownership handover
|
|
572
|
+
* @param {?WriteParams} [params]
|
|
573
|
+
* @returns {Promise<void>}
|
|
574
|
+
*/
|
|
575
|
+
public async completeOwnershipHandover(
|
|
576
|
+
pendingOwner: Address,
|
|
577
|
+
params?: WriteParams,
|
|
578
|
+
) {
|
|
579
|
+
return await this.awaitResult(
|
|
580
|
+
this.completeOwnershipHandoverRaw(pendingOwner, params),
|
|
581
|
+
);
|
|
582
|
+
}
|
|
583
|
+
|
|
584
|
+
/**
|
|
585
|
+
* Complete a pending ownership handover to a new owner
|
|
586
|
+
* Must be called by the current owner after the new owner has requested the handover
|
|
587
|
+
*
|
|
588
|
+
* @public
|
|
589
|
+
* @async
|
|
590
|
+
* @param {Address} pendingOwner - The address that requested the ownership handover
|
|
591
|
+
* @param {?WriteParams} [params]
|
|
592
|
+
* @returns {Promise<{ hash: `0x${string}`; result: void; }>}
|
|
593
|
+
*/
|
|
594
|
+
public async completeOwnershipHandoverRaw(
|
|
595
|
+
pendingOwner: Address,
|
|
596
|
+
params?: WriteParams,
|
|
597
|
+
) {
|
|
598
|
+
const { request, result } =
|
|
599
|
+
await simulateOwnableRolesCompleteOwnershipHandover(this._config, {
|
|
600
|
+
address: this.assertValidAddress(),
|
|
601
|
+
args: [pendingOwner],
|
|
602
|
+
...this.optionallyAttachAccount(),
|
|
603
|
+
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
604
|
+
...(params as any),
|
|
605
|
+
});
|
|
606
|
+
const hash = await writeOwnableRolesCompleteOwnershipHandover(
|
|
607
|
+
this._config,
|
|
608
|
+
request,
|
|
609
|
+
);
|
|
610
|
+
return { hash, result };
|
|
611
|
+
}
|
|
612
|
+
|
|
613
|
+
/**
|
|
614
|
+
* Cancel a pending ownership handover request
|
|
615
|
+
* Must be called by the account that originally requested the handover
|
|
616
|
+
*
|
|
617
|
+
* @public
|
|
618
|
+
* @async
|
|
619
|
+
* @param {?WriteParams} [params]
|
|
620
|
+
* @returns {Promise<void>}
|
|
621
|
+
*/
|
|
622
|
+
public async cancelOwnershipHandover(params?: WriteParams) {
|
|
623
|
+
return await this.awaitResult(this.cancelOwnershipHandoverRaw(params));
|
|
624
|
+
}
|
|
625
|
+
|
|
626
|
+
/**
|
|
627
|
+
* Cancel a pending ownership handover request
|
|
628
|
+
* Must be called by the account that originally requested the handover
|
|
629
|
+
*
|
|
630
|
+
* @public
|
|
631
|
+
* @async
|
|
632
|
+
* @param {?WriteParams} [params]
|
|
633
|
+
* @returns {Promise<{ hash: `0x${string}`; result: void; }>}
|
|
634
|
+
*/
|
|
635
|
+
public async cancelOwnershipHandoverRaw(params?: WriteParams) {
|
|
636
|
+
const { request, result } =
|
|
637
|
+
await simulateOwnableRolesCancelOwnershipHandover(this._config, {
|
|
638
|
+
address: this.assertValidAddress(),
|
|
639
|
+
...this.optionallyAttachAccount(),
|
|
640
|
+
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
641
|
+
...(params as any),
|
|
642
|
+
});
|
|
643
|
+
const hash = await writeOwnableRolesCancelOwnershipHandover(
|
|
644
|
+
this._config,
|
|
645
|
+
request,
|
|
646
|
+
);
|
|
647
|
+
return { hash, result };
|
|
648
|
+
}
|
|
649
|
+
|
|
650
|
+
/**
|
|
651
|
+
* Get the expiry timestamp for a pending ownership handover
|
|
652
|
+
* Returns 0 if there is no pending handover request for the given address
|
|
653
|
+
*
|
|
654
|
+
* @public
|
|
655
|
+
* @param {Address} pendingOwner - The address to check for pending handover requests
|
|
656
|
+
* @param {?ReadParams} [params]
|
|
657
|
+
* @returns {Promise<bigint>} - The timestamp when the handover request expires, or 0 if no request exists
|
|
658
|
+
*/
|
|
659
|
+
public ownershipHandoverExpiresAt(
|
|
660
|
+
pendingOwner: Address,
|
|
661
|
+
params?: ReadParams,
|
|
662
|
+
): Promise<bigint> {
|
|
663
|
+
return readOwnableRolesOwnershipHandoverExpiresAt(this._config, {
|
|
664
|
+
address: this.assertValidAddress(),
|
|
665
|
+
args: [pendingOwner],
|
|
666
|
+
...this.optionallyAttachAccount(),
|
|
667
|
+
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
668
|
+
...(params as any),
|
|
669
|
+
});
|
|
670
|
+
}
|
|
671
|
+
|
|
672
|
+
/**
|
|
673
|
+
* Allow the caller to remove their own roles
|
|
674
|
+
* If the caller does not have a role, then it will be a no-op for that role
|
|
675
|
+
*
|
|
676
|
+
* @public
|
|
677
|
+
* @async
|
|
678
|
+
* @param {Roles} roles - Bitmap of roles to renounce
|
|
679
|
+
* @param {?WriteParams} [params]
|
|
680
|
+
* @returns {Promise<void>}
|
|
681
|
+
*/
|
|
682
|
+
public async renounceRoles(roles: Roles, params?: WriteParams) {
|
|
683
|
+
return await this.awaitResult(this.renounceRolesRaw(roles, params));
|
|
684
|
+
}
|
|
685
|
+
|
|
686
|
+
/**
|
|
687
|
+
* Allow the caller to remove their own roles
|
|
688
|
+
* If the caller does not have a role, then it will be a no-op for that role
|
|
689
|
+
*
|
|
690
|
+
* @public
|
|
691
|
+
* @async
|
|
692
|
+
* @param {Roles} roles - Bitmap of roles to renounce
|
|
693
|
+
* @param {?WriteParams} [params]
|
|
694
|
+
* @returns {Promise<{ hash: `0x${string}`; result: void; }>}
|
|
695
|
+
*/
|
|
696
|
+
public async renounceRolesRaw(roles: Roles, params?: WriteParams) {
|
|
697
|
+
const { request, result } = await simulateOwnableRolesRenounceRoles(
|
|
698
|
+
this._config,
|
|
699
|
+
{
|
|
700
|
+
address: this.assertValidAddress(),
|
|
701
|
+
args: [roles],
|
|
702
|
+
...this.optionallyAttachAccount(),
|
|
703
|
+
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
704
|
+
...(params as any),
|
|
705
|
+
},
|
|
706
|
+
);
|
|
707
|
+
const hash = await writeOwnableRolesRenounceRoles(this._config, request);
|
|
708
|
+
return { hash, result };
|
|
709
|
+
}
|
|
429
710
|
}
|
|
@@ -37,6 +37,7 @@ describe("AllowListIncentive", () => {
|
|
|
37
37
|
reward: 1n,
|
|
38
38
|
limit: 1n,
|
|
39
39
|
});
|
|
40
|
+
// @ts-expect-error
|
|
40
41
|
await action.deploy();
|
|
41
42
|
expect(isAddress(action.assertValidAddress())).toBe(true);
|
|
42
43
|
});
|
|
@@ -186,4 +187,51 @@ describe("AllowListIncentive", () => {
|
|
|
186
187
|
expect(e).toBeInstanceOf(Error);
|
|
187
188
|
}
|
|
188
189
|
});
|
|
190
|
+
|
|
191
|
+
test("isClaimable returns expected values", async () => {
|
|
192
|
+
const referrer = accounts[1].account;
|
|
193
|
+
const trustedSigner = accounts[0];
|
|
194
|
+
const allowList = await loadFixture(freshAllowList(fixtures));
|
|
195
|
+
const allowListIncentive = new fixtures.bases.AllowListIncentive(
|
|
196
|
+
defaultOptions,
|
|
197
|
+
{
|
|
198
|
+
allowList: allowList.assertValidAddress(),
|
|
199
|
+
limit: 1n,
|
|
200
|
+
},
|
|
201
|
+
);
|
|
202
|
+
const boost = await freshBoost(fixtures, {
|
|
203
|
+
incentives: [allowListIncentive],
|
|
204
|
+
});
|
|
205
|
+
await allowList.grantManyRoles(
|
|
206
|
+
[allowListIncentive.assertValidAddress()],
|
|
207
|
+
[Roles.MANAGER],
|
|
208
|
+
);
|
|
209
|
+
|
|
210
|
+
const claimant = trustedSigner.account;
|
|
211
|
+
const incentiveData = allowListIncentive.buildClaimData();
|
|
212
|
+
|
|
213
|
+
// Should be claimable before claiming
|
|
214
|
+
expect(await boost.incentives[0]!.isClaimable({ target: claimant })).toBe(true);
|
|
215
|
+
|
|
216
|
+
const claimDataPayload = await boost.validator.encodeClaimData({
|
|
217
|
+
signer: trustedSigner,
|
|
218
|
+
incentiveData,
|
|
219
|
+
chainId: defaultOptions.config.chains[0].id,
|
|
220
|
+
incentiveQuantity: boost.incentives.length,
|
|
221
|
+
claimant,
|
|
222
|
+
boostId: boost.id,
|
|
223
|
+
});
|
|
224
|
+
|
|
225
|
+
// Claim the incentive
|
|
226
|
+
await fixtures.core.claimIncentive(
|
|
227
|
+
boost.id,
|
|
228
|
+
0n,
|
|
229
|
+
referrer,
|
|
230
|
+
claimDataPayload,
|
|
231
|
+
{ value: parseEther("0.000075"), account: trustedSigner.privateKey },
|
|
232
|
+
);
|
|
233
|
+
|
|
234
|
+
// Should not be claimable after claiming
|
|
235
|
+
expect(await boost.incentives[0]!.isClaimable({ target: claimant })).toBe(false);
|
|
236
|
+
});
|
|
189
237
|
});
|
|
@@ -272,7 +272,7 @@ export class AllowListIncentive extends DeployableTarget<
|
|
|
272
272
|
) {
|
|
273
273
|
return await readAllowListIncentiveIsClaimable(this._config, {
|
|
274
274
|
address: this.assertValidAddress(),
|
|
275
|
-
args: [
|
|
275
|
+
args: [payload.target, '0x'],
|
|
276
276
|
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
277
277
|
...(params as any),
|
|
278
278
|
});
|
|
@@ -33,6 +33,7 @@ describe("CGDAIncentive", () => {
|
|
|
33
33
|
rewardDecay: 1n,
|
|
34
34
|
manager: budgets.budget.address || zeroAddress,
|
|
35
35
|
});
|
|
36
|
+
// @ts-expect-error
|
|
36
37
|
await action.deploy();
|
|
37
38
|
expect(isAddress(action.assertValidAddress())).toBe(true);
|
|
38
39
|
});
|
|
@@ -208,4 +209,53 @@ describe("CGDAIncentive", () => {
|
|
|
208
209
|
true,
|
|
209
210
|
);
|
|
210
211
|
});
|
|
212
|
+
|
|
213
|
+
test("isClaimable returns expected values", async () => {
|
|
214
|
+
const referrer = accounts[1].account;
|
|
215
|
+
const trustedSigner = accounts[0];
|
|
216
|
+
const cgdaIncentive = fixtures.core.CGDAIncentive({
|
|
217
|
+
asset: budgets.erc20.assertValidAddress(),
|
|
218
|
+
initialReward: 1n,
|
|
219
|
+
totalBudget: 10n,
|
|
220
|
+
rewardBoost: 1n,
|
|
221
|
+
rewardDecay: 1n,
|
|
222
|
+
manager: budgets.budget.assertValidAddress(),
|
|
223
|
+
});
|
|
224
|
+
const boost = await freshBoost(fixtures, {
|
|
225
|
+
budget: budgets.budget,
|
|
226
|
+
incentives: [cgdaIncentive],
|
|
227
|
+
});
|
|
228
|
+
|
|
229
|
+
const claimant = trustedSigner.account;
|
|
230
|
+
const incentiveData = cgdaIncentive.buildClaimData();
|
|
231
|
+
|
|
232
|
+
// Should be claimable before claiming
|
|
233
|
+
expect(await boost.incentives[0]!.isClaimable({
|
|
234
|
+
target: claimant,
|
|
235
|
+
data: incentiveData
|
|
236
|
+
})).toBe(true);
|
|
237
|
+
|
|
238
|
+
const claimDataPayload = await boost.validator.encodeClaimData({
|
|
239
|
+
signer: trustedSigner,
|
|
240
|
+
incentiveData,
|
|
241
|
+
chainId: defaultOptions.config.chains[0].id,
|
|
242
|
+
incentiveQuantity: boost.incentives.length,
|
|
243
|
+
claimant,
|
|
244
|
+
boostId: boost.id,
|
|
245
|
+
});
|
|
246
|
+
|
|
247
|
+
// Claim the incentive
|
|
248
|
+
await fixtures.core.claimIncentive(
|
|
249
|
+
boost.id,
|
|
250
|
+
0n,
|
|
251
|
+
referrer,
|
|
252
|
+
claimDataPayload,
|
|
253
|
+
);
|
|
254
|
+
|
|
255
|
+
// Should not be claimable after claiming
|
|
256
|
+
expect(await boost.incentives[0]!.isClaimable({
|
|
257
|
+
target: claimant,
|
|
258
|
+
data: incentiveData
|
|
259
|
+
})).toBe(false);
|
|
260
|
+
});
|
|
211
261
|
});
|
|
@@ -375,7 +375,7 @@ export class CGDAIncentive extends DeployableTarget<
|
|
|
375
375
|
public async isClaimable(payload: ClaimPayload, params?: ReadParams) {
|
|
376
376
|
return await readCgdaIncentiveIsClaimable(this._config, {
|
|
377
377
|
address: this.assertValidAddress(),
|
|
378
|
-
args: [
|
|
378
|
+
args: [payload.target, payload.data],
|
|
379
379
|
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
380
380
|
...(params as any),
|
|
381
381
|
});
|
|
@@ -359,7 +359,7 @@ export class ERC1155Incentive extends DeployableTarget<
|
|
|
359
359
|
public async isClaimable(payload: ClaimPayload, params?: ReadParams) {
|
|
360
360
|
return await readErc1155IncentiveIsClaimable(this._config, {
|
|
361
361
|
address: this.assertValidAddress(),
|
|
362
|
-
args: [
|
|
362
|
+
args: [payload.target, payload.data],
|
|
363
363
|
// biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
|
|
364
364
|
...(params as any),
|
|
365
365
|
});
|
|
@@ -39,6 +39,7 @@ describe("ERC20Incentive", () => {
|
|
|
39
39
|
limit: 1n,
|
|
40
40
|
manager: zeroAddress,
|
|
41
41
|
});
|
|
42
|
+
// @ts-expect-error
|
|
42
43
|
await action.deploy();
|
|
43
44
|
expect(isAddress(action.assertValidAddress())).toBe(true);
|
|
44
45
|
});
|
|
@@ -205,4 +206,52 @@ describe("ERC20Incentive", () => {
|
|
|
205
206
|
true,
|
|
206
207
|
);
|
|
207
208
|
});
|
|
209
|
+
|
|
210
|
+
test("isClaimable returns expected values", async () => {
|
|
211
|
+
const referrer = accounts[1].account;
|
|
212
|
+
const trustedSigner = accounts[0];
|
|
213
|
+
const erc20Incentive = fixtures.core.ERC20Incentive({
|
|
214
|
+
asset: budgets.erc20.assertValidAddress(),
|
|
215
|
+
strategy: StrategyType.POOL,
|
|
216
|
+
reward: 1n,
|
|
217
|
+
limit: 1n,
|
|
218
|
+
manager: budgets.budget.assertValidAddress(),
|
|
219
|
+
});
|
|
220
|
+
const boost = await freshBoost(fixtures, {
|
|
221
|
+
budget: budgets.budget,
|
|
222
|
+
incentives: [erc20Incentive],
|
|
223
|
+
});
|
|
224
|
+
|
|
225
|
+
const claimant = trustedSigner.account;
|
|
226
|
+
const incentiveData = erc20Incentive.buildClaimData();
|
|
227
|
+
|
|
228
|
+
// Should be claimable before claiming
|
|
229
|
+
expect(await boost.incentives[0]!.isClaimable({
|
|
230
|
+
target: claimant,
|
|
231
|
+
data: incentiveData
|
|
232
|
+
})).toBe(true);
|
|
233
|
+
|
|
234
|
+
const claimDataPayload = await boost.validator.encodeClaimData({
|
|
235
|
+
signer: trustedSigner,
|
|
236
|
+
incentiveData,
|
|
237
|
+
chainId: defaultOptions.config.chains[0].id,
|
|
238
|
+
incentiveQuantity: boost.incentives.length,
|
|
239
|
+
claimant,
|
|
240
|
+
boostId: boost.id,
|
|
241
|
+
});
|
|
242
|
+
|
|
243
|
+
// Claim the incentive
|
|
244
|
+
await fixtures.core.claimIncentive(
|
|
245
|
+
boost.id,
|
|
246
|
+
0n,
|
|
247
|
+
referrer,
|
|
248
|
+
claimDataPayload,
|
|
249
|
+
);
|
|
250
|
+
|
|
251
|
+
// Should not be claimable after claiming
|
|
252
|
+
expect(await boost.incentives[0]!.isClaimable({
|
|
253
|
+
target: claimant,
|
|
254
|
+
data: incentiveData
|
|
255
|
+
})).toBe(false);
|
|
256
|
+
});
|
|
208
257
|
});
|