@boostxyz/sdk 0.0.0-alpha.2 → 0.0.0-alpha.21

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.
Files changed (271) hide show
  1. package/dist/Actions/Action.cjs +2 -1
  2. package/dist/Actions/Action.cjs.map +1 -0
  3. package/dist/Actions/Action.d.ts +1 -1
  4. package/dist/Actions/Action.d.ts.map +1 -1
  5. package/dist/Actions/Action.js +14 -12
  6. package/dist/Actions/Action.js.map +1 -0
  7. package/dist/Actions/ContractAction.d.ts +57 -14
  8. package/dist/Actions/ContractAction.d.ts.map +1 -1
  9. package/dist/Actions/ERC721MintAction.d.ts +50 -23
  10. package/dist/Actions/ERC721MintAction.d.ts.map +1 -1
  11. package/dist/Actions/EventAction.cjs +2 -1
  12. package/dist/Actions/EventAction.cjs.map +1 -0
  13. package/dist/Actions/EventAction.d.ts +405 -36
  14. package/dist/Actions/EventAction.d.ts.map +1 -1
  15. package/dist/Actions/EventAction.js +15 -209
  16. package/dist/Actions/EventAction.js.map +1 -0
  17. package/dist/AllowLists/AllowList.cjs +2 -1
  18. package/dist/AllowLists/AllowList.cjs.map +1 -0
  19. package/dist/AllowLists/AllowList.d.ts +6 -5
  20. package/dist/AllowLists/AllowList.d.ts.map +1 -1
  21. package/dist/AllowLists/AllowList.js +46 -22
  22. package/dist/AllowLists/AllowList.js.map +1 -0
  23. package/dist/AllowLists/OpenAllowList.d.ts +423 -0
  24. package/dist/AllowLists/OpenAllowList.d.ts.map +1 -0
  25. package/dist/AllowLists/SimpleAllowList.cjs +2 -1
  26. package/dist/AllowLists/SimpleAllowList.cjs.map +1 -0
  27. package/dist/AllowLists/SimpleAllowList.d.ts +124 -40
  28. package/dist/AllowLists/SimpleAllowList.d.ts.map +1 -1
  29. package/dist/AllowLists/SimpleAllowList.js +76 -76
  30. package/dist/AllowLists/SimpleAllowList.js.map +1 -0
  31. package/dist/AllowLists/SimpleDenyList.cjs +2 -1
  32. package/dist/AllowLists/SimpleDenyList.cjs.map +1 -0
  33. package/dist/AllowLists/SimpleDenyList.d.ts +234 -13
  34. package/dist/AllowLists/SimpleDenyList.d.ts.map +1 -1
  35. package/dist/AllowLists/SimpleDenyList.js +12 -200
  36. package/dist/AllowLists/SimpleDenyList.js.map +1 -0
  37. package/dist/Auth/Auth.cjs +1 -0
  38. package/dist/Auth/Auth.cjs.map +1 -0
  39. package/dist/Auth/Auth.js +1 -0
  40. package/dist/Auth/Auth.js.map +1 -0
  41. package/dist/Auth/PassthroughAuth.cjs +2 -1
  42. package/dist/Auth/PassthroughAuth.cjs.map +1 -0
  43. package/dist/Auth/PassthroughAuth.js +5 -4
  44. package/dist/Auth/PassthroughAuth.js.map +1 -0
  45. package/dist/Boost.cjs +2 -1
  46. package/dist/Boost.cjs.map +1 -0
  47. package/dist/Boost.d.ts +105 -14
  48. package/dist/Boost.d.ts.map +1 -1
  49. package/dist/Boost.js +138 -5
  50. package/dist/Boost.js.map +1 -0
  51. package/dist/BoostCore-DolmDuXW.cjs +3 -0
  52. package/dist/BoostCore-DolmDuXW.cjs.map +1 -0
  53. package/dist/BoostCore-Z97KVu4V.js +1448 -0
  54. package/dist/BoostCore-Z97KVu4V.js.map +1 -0
  55. package/dist/BoostCore.cjs +2 -2
  56. package/dist/BoostCore.cjs.map +1 -0
  57. package/dist/BoostCore.d.ts +788 -79
  58. package/dist/BoostCore.d.ts.map +1 -1
  59. package/dist/BoostCore.js +30 -1103
  60. package/dist/BoostCore.js.map +1 -0
  61. package/dist/BoostRegistry.cjs +2 -1
  62. package/dist/BoostRegistry.cjs.map +1 -0
  63. package/dist/BoostRegistry.d.ts +95 -26
  64. package/dist/BoostRegistry.d.ts.map +1 -1
  65. package/dist/BoostRegistry.js +183 -89
  66. package/dist/BoostRegistry.js.map +1 -0
  67. package/dist/Budgets/Budget.cjs +2 -1
  68. package/dist/Budgets/Budget.cjs.map +1 -0
  69. package/dist/Budgets/Budget.d.ts +1 -1
  70. package/dist/Budgets/Budget.d.ts.map +1 -1
  71. package/dist/Budgets/Budget.js +15 -13
  72. package/dist/Budgets/Budget.js.map +1 -0
  73. package/dist/Budgets/ManagedBudget.cjs +2 -1
  74. package/dist/Budgets/ManagedBudget.cjs.map +1 -0
  75. package/dist/Budgets/ManagedBudget.d.ts +112 -192
  76. package/dist/Budgets/ManagedBudget.d.ts.map +1 -1
  77. package/dist/Budgets/ManagedBudget.js +91 -291
  78. package/dist/Budgets/ManagedBudget.js.map +1 -0
  79. package/dist/Budgets/VestingBudget.d.ts +277 -91
  80. package/dist/Budgets/VestingBudget.d.ts.map +1 -1
  81. package/dist/Deployable/Contract.cjs +2 -1
  82. package/dist/Deployable/Contract.cjs.map +1 -0
  83. package/dist/Deployable/Contract.d.ts +4 -5
  84. package/dist/Deployable/Contract.d.ts.map +1 -1
  85. package/dist/Deployable/Contract.js +7 -8
  86. package/dist/Deployable/Contract.js.map +1 -0
  87. package/dist/Deployable/Deployable.cjs +1 -0
  88. package/dist/Deployable/Deployable.cjs.map +1 -0
  89. package/dist/Deployable/Deployable.d.ts +9 -3
  90. package/dist/Deployable/Deployable.d.ts.map +1 -1
  91. package/dist/Deployable/Deployable.js +10 -5
  92. package/dist/Deployable/Deployable.js.map +1 -0
  93. package/dist/Deployable/DeployableTarget.cjs +2 -1
  94. package/dist/Deployable/DeployableTarget.cjs.map +1 -0
  95. package/dist/Deployable/DeployableTarget.d.ts +16 -15
  96. package/dist/Deployable/DeployableTarget.d.ts.map +1 -1
  97. package/dist/Deployable/DeployableTarget.js +49 -42
  98. package/dist/Deployable/DeployableTarget.js.map +1 -0
  99. package/dist/Deployable/DeployableTargetWithRBAC.cjs +2 -0
  100. package/dist/Deployable/DeployableTargetWithRBAC.cjs.map +1 -0
  101. package/dist/Deployable/DeployableTargetWithRBAC.d.ts +179 -0
  102. package/dist/Deployable/DeployableTargetWithRBAC.d.ts.map +1 -0
  103. package/dist/Deployable/DeployableTargetWithRBAC.js +222 -0
  104. package/dist/Deployable/DeployableTargetWithRBAC.js.map +1 -0
  105. package/dist/EventAction-CBKzuNoN.cjs +2 -0
  106. package/dist/EventAction-CBKzuNoN.cjs.map +1 -0
  107. package/dist/EventAction-DWuuc_Qy.js +1528 -0
  108. package/dist/EventAction-DWuuc_Qy.js.map +1 -0
  109. package/dist/Incentive-BxzEtN26.js +298 -0
  110. package/dist/Incentive-BxzEtN26.js.map +1 -0
  111. package/dist/Incentive-CrF3-ayL.cjs +2 -0
  112. package/dist/Incentive-CrF3-ayL.cjs.map +1 -0
  113. package/dist/Incentives/AllowListIncentive.cjs +2 -1
  114. package/dist/Incentives/AllowListIncentive.cjs.map +1 -0
  115. package/dist/Incentives/AllowListIncentive.d.ts +65 -21
  116. package/dist/Incentives/AllowListIncentive.d.ts.map +1 -1
  117. package/dist/Incentives/AllowListIncentive.js +52 -36
  118. package/dist/Incentives/AllowListIncentive.js.map +1 -0
  119. package/dist/Incentives/CGDAIncentive.cjs +2 -1
  120. package/dist/Incentives/CGDAIncentive.cjs.map +1 -0
  121. package/dist/Incentives/CGDAIncentive.d.ts +315 -26
  122. package/dist/Incentives/CGDAIncentive.d.ts.map +1 -1
  123. package/dist/Incentives/CGDAIncentive.js +64 -39
  124. package/dist/Incentives/CGDAIncentive.js.map +1 -0
  125. package/dist/Incentives/ERC1155Incentive.d.ts +291 -43
  126. package/dist/Incentives/ERC1155Incentive.d.ts.map +1 -1
  127. package/dist/Incentives/ERC20Incentive.cjs +2 -1
  128. package/dist/Incentives/ERC20Incentive.cjs.map +1 -0
  129. package/dist/Incentives/ERC20Incentive.d.ts +270 -33
  130. package/dist/Incentives/ERC20Incentive.d.ts.map +1 -1
  131. package/dist/Incentives/ERC20Incentive.js +69 -46
  132. package/dist/Incentives/ERC20Incentive.js.map +1 -0
  133. package/dist/{Budgets/SimpleBudget.d.ts → Incentives/ERC20VariableCriteriaIncentive.d.ts} +338 -421
  134. package/dist/Incentives/ERC20VariableCriteriaIncentive.d.ts.map +1 -0
  135. package/dist/Incentives/ERC20VariableIncentive.d.ts +262 -32
  136. package/dist/Incentives/ERC20VariableIncentive.d.ts.map +1 -1
  137. package/dist/Incentives/Incentive.cjs +2 -1
  138. package/dist/Incentives/Incentive.cjs.map +1 -0
  139. package/dist/Incentives/Incentive.d.ts +5 -8
  140. package/dist/Incentives/Incentive.d.ts.map +1 -1
  141. package/dist/Incentives/Incentive.js +17 -278
  142. package/dist/Incentives/Incentive.js.map +1 -0
  143. package/dist/Incentives/PointsIncentive.cjs +2 -1
  144. package/dist/Incentives/PointsIncentive.cjs.map +1 -0
  145. package/dist/Incentives/PointsIncentive.d.ts +81 -23
  146. package/dist/Incentives/PointsIncentive.d.ts.map +1 -1
  147. package/dist/Incentives/PointsIncentive.js +57 -36
  148. package/dist/Incentives/PointsIncentive.js.map +1 -0
  149. package/dist/SimpleDenyList-BUR17Tt1.cjs +2 -0
  150. package/dist/SimpleDenyList-BUR17Tt1.cjs.map +1 -0
  151. package/dist/SimpleDenyList-CGaWjuld.js +132 -0
  152. package/dist/SimpleDenyList-CGaWjuld.js.map +1 -0
  153. package/dist/Validators/SignerValidator.cjs +2 -1
  154. package/dist/Validators/SignerValidator.cjs.map +1 -0
  155. package/dist/Validators/SignerValidator.d.ts +310 -17
  156. package/dist/Validators/SignerValidator.d.ts.map +1 -1
  157. package/dist/Validators/SignerValidator.js +165 -36
  158. package/dist/Validators/SignerValidator.js.map +1 -0
  159. package/dist/Validators/Validator.cjs +2 -1
  160. package/dist/Validators/Validator.cjs.map +1 -0
  161. package/dist/Validators/Validator.d.ts +2 -2
  162. package/dist/Validators/Validator.d.ts.map +1 -1
  163. package/dist/Validators/Validator.js +10 -8
  164. package/dist/Validators/Validator.js.map +1 -0
  165. package/dist/claiming.cjs +2 -0
  166. package/dist/claiming.cjs.map +1 -0
  167. package/dist/claiming.d.ts +43 -0
  168. package/dist/claiming.d.ts.map +1 -0
  169. package/dist/claiming.js +17 -0
  170. package/dist/claiming.js.map +1 -0
  171. package/dist/componentInterfaces-BBCFkrZv.js +14 -0
  172. package/dist/componentInterfaces-BBCFkrZv.js.map +1 -0
  173. package/dist/componentInterfaces-DRI_dQ-P.cjs +2 -0
  174. package/dist/componentInterfaces-DRI_dQ-P.cjs.map +1 -0
  175. package/dist/deployments-DVXioW2i.cjs +2 -0
  176. package/dist/deployments-DVXioW2i.cjs.map +1 -0
  177. package/dist/deployments-oykLv3_Z.js +43 -0
  178. package/dist/deployments-oykLv3_Z.js.map +1 -0
  179. package/dist/deployments.json +44 -0
  180. package/dist/errors.cjs +2 -1
  181. package/dist/errors.cjs.map +1 -0
  182. package/dist/errors.d.ts +421 -1
  183. package/dist/errors.d.ts.map +1 -1
  184. package/dist/errors.js +297 -39
  185. package/dist/errors.js.map +1 -0
  186. package/dist/{generated-x_abr3Yv.js → generated-CKt2yCQd.js} +3143 -3002
  187. package/dist/generated-CKt2yCQd.js.map +1 -0
  188. package/dist/generated-CyTNlOwM.cjs +3 -0
  189. package/dist/generated-CyTNlOwM.cjs.map +1 -0
  190. package/dist/index.cjs +2 -1
  191. package/dist/index.cjs.map +1 -0
  192. package/dist/index.d.ts +10 -9
  193. package/dist/index.d.ts.map +1 -1
  194. package/dist/index.js +144 -1353
  195. package/dist/index.js.map +1 -0
  196. package/dist/transfers.cjs +2 -0
  197. package/dist/transfers.cjs.map +1 -0
  198. package/dist/transfers.d.ts +198 -0
  199. package/dist/transfers.d.ts.map +1 -0
  200. package/dist/transfers.js +84 -0
  201. package/dist/transfers.js.map +1 -0
  202. package/dist/utils.cjs +2 -1
  203. package/dist/utils.cjs.map +1 -0
  204. package/dist/utils.d.ts +26 -1350
  205. package/dist/utils.d.ts.map +1 -1
  206. package/dist/utils.js +38 -636
  207. package/dist/utils.js.map +1 -0
  208. package/package.json +37 -11
  209. package/src/Actions/Action.test.ts +79 -0
  210. package/src/Actions/Action.ts +61 -0
  211. package/src/Actions/ContractAction.test.ts +197 -0
  212. package/src/Actions/ContractAction.ts +300 -0
  213. package/src/Actions/ERC721MintAction.test.ts +112 -0
  214. package/src/Actions/ERC721MintAction.ts +291 -0
  215. package/src/Actions/EventAction.test.ts +787 -0
  216. package/src/Actions/EventAction.ts +1218 -0
  217. package/src/AllowLists/AllowList.test.ts +64 -0
  218. package/src/AllowLists/AllowList.ts +62 -0
  219. package/src/AllowLists/OpenAllowList.test.ts +40 -0
  220. package/src/AllowLists/OpenAllowList.ts +45 -0
  221. package/src/AllowLists/SimpleAllowList.test.ts +52 -0
  222. package/src/AllowLists/SimpleAllowList.ts +262 -0
  223. package/src/AllowLists/SimpleDenyList.test.ts +52 -0
  224. package/src/AllowLists/SimpleDenyList.ts +250 -0
  225. package/src/Auth/Auth.ts +11 -0
  226. package/src/Auth/PassthroughAuth.test.ts +12 -0
  227. package/src/Auth/PassthroughAuth.ts +80 -0
  228. package/src/Boost.ts +287 -0
  229. package/src/BoostCore.test.ts +894 -0
  230. package/src/BoostCore.ts +1438 -0
  231. package/src/BoostRegistry.test.ts +53 -0
  232. package/src/BoostRegistry.ts +588 -0
  233. package/src/Budgets/Budget.test.ts +27 -0
  234. package/src/Budgets/Budget.ts +60 -0
  235. package/src/Budgets/ManagedBudget.test.ts +217 -0
  236. package/src/Budgets/ManagedBudget.ts +534 -0
  237. package/src/Budgets/VestingBudget.test.ts +123 -0
  238. package/src/Budgets/VestingBudget.ts +530 -0
  239. package/src/Deployable/Contract.ts +228 -0
  240. package/src/Deployable/Deployable.ts +250 -0
  241. package/src/Deployable/DeployableTarget.ts +234 -0
  242. package/src/Deployable/DeployableTargetWithRBAC.ts +323 -0
  243. package/src/Incentives/AllowListIncentive.test.ts +143 -0
  244. package/src/Incentives/AllowListIncentive.ts +336 -0
  245. package/src/Incentives/CGDAIncentive.test.ts +135 -0
  246. package/src/Incentives/CGDAIncentive.ts +476 -0
  247. package/src/Incentives/ERC1155Incentive.test.ts +87 -0
  248. package/src/Incentives/ERC1155Incentive.ts +465 -0
  249. package/src/Incentives/ERC20Incentive.test.ts +133 -0
  250. package/src/Incentives/ERC20Incentive.ts +490 -0
  251. package/src/Incentives/ERC20VariableCriteriaIncentive.test.ts +184 -0
  252. package/src/Incentives/ERC20VariableCriteriaIncentive.ts +309 -0
  253. package/src/Incentives/ERC20VariableIncentive.test.ts +139 -0
  254. package/src/Incentives/ERC20VariableIncentive.ts +428 -0
  255. package/src/Incentives/Incentive.test.ts +95 -0
  256. package/src/Incentives/Incentive.ts +86 -0
  257. package/src/Incentives/PointsIncentive.test.ts +138 -0
  258. package/src/Incentives/PointsIncentive.ts +367 -0
  259. package/src/Validators/SignerValidator.test.ts +159 -0
  260. package/src/Validators/SignerValidator.ts +683 -0
  261. package/src/Validators/Validator.test.ts +21 -0
  262. package/src/Validators/Validator.ts +55 -0
  263. package/src/claiming.ts +56 -0
  264. package/src/errors.ts +866 -0
  265. package/src/index.test.ts +122 -0
  266. package/src/index.ts +58 -0
  267. package/src/transfers.ts +284 -0
  268. package/src/utils.test.ts +44 -0
  269. package/src/utils.ts +247 -0
  270. package/dist/Budgets/SimpleBudget.d.ts.map +0 -1
  271. package/dist/generated-BaaleHW-.cjs +0 -2
@@ -0,0 +1,228 @@
1
+ import { type Config, watchContractEvent } from '@wagmi/core';
2
+ import type { ExtractAbiEvent } from 'abitype';
3
+ import {
4
+ type Abi,
5
+ type Address,
6
+ type ContractEventName,
7
+ type GetLogsReturnType,
8
+ type WaitForTransactionReceiptParameters,
9
+ type WatchContractEventOnLogsParameter,
10
+ getAbiItem,
11
+ } from 'viem';
12
+ import { getLogs } from 'viem/actions';
13
+ import { ContractAddressRequiredError } from '../errors';
14
+ import {
15
+ type GetLogsParams,
16
+ type HashAndSimulatedResult,
17
+ type WatchParams,
18
+ awaitResult,
19
+ } from '../utils';
20
+
21
+ /**
22
+ * A basic Contract class to encapsulate configuration and a potential address
23
+ *
24
+ * @export
25
+ * @class Contract
26
+ * @typedef {Contract}
27
+ * @template {Abi} [ContractAbi=[]]
28
+ * @template {ContractEventName<ContractAbi>} [ContractEvent=any]
29
+ */
30
+ export class Contract<ContractAbi extends Abi> {
31
+ //@ts-expect-error this should always be set by implementing contract
32
+ public readonly abi: ContractAbi;
33
+ /**
34
+ * @see [Wagmi Configuration](https://wagmi.sh/core/api/createConfig)
35
+ * @protected
36
+ * @type {WagmiConfig}
37
+ */
38
+ protected _config: Config;
39
+ /**
40
+ * The internally managed address for this contract
41
+ *
42
+ * @protected
43
+ * @type {(Address | undefined)}
44
+ */
45
+ protected _address: Address | undefined;
46
+
47
+ /**
48
+ * Creates an instance of Contract.
49
+ *
50
+ * @constructor
51
+ * @param {Config} config
52
+ * @param {(Address | undefined)} address
53
+ */
54
+ constructor(config: Config, address: Address | undefined) {
55
+ this._config = config;
56
+ this._address = address;
57
+ }
58
+
59
+ /**
60
+ * A getter returning this contract's deployed address, if it exists.
61
+ *
62
+ * @public
63
+ * @readonly
64
+ * @type {Address | undefined}
65
+ */
66
+ public get address() {
67
+ return this._address;
68
+ }
69
+
70
+ /**
71
+ * Will set this contract's address and return the instance for chaining. Does not verify that provided address is valid.
72
+ *
73
+ * @public
74
+ * @param {Address} address
75
+ * @returns {this}
76
+ */
77
+ public at(address: Address) {
78
+ this._address = address;
79
+ return this;
80
+ }
81
+
82
+ /**
83
+ * Will set this contract's internal [Wagmi Configuration](https://en.wikipedia.org/wiki/Factorial) and return the instance for chaining.
84
+ *
85
+ * @public
86
+ * @param {Config} config
87
+ * @returns {this}
88
+ */
89
+ public withConfig(config: Config) {
90
+ this._config = config;
91
+ return this;
92
+ }
93
+
94
+ /**
95
+ * Utility function to validate the existence of an address on this Contract.
96
+ *
97
+ * @public
98
+ * @returns {Address}
99
+ * @throws {@link ContractAddressRequiredError} if no address exists on this Contract instance
100
+ */
101
+ public assertValidAddress() {
102
+ const address = this.address;
103
+ if (!address) throw new ContractAddressRequiredError();
104
+ return address;
105
+ }
106
+
107
+ /**
108
+ * A typed wrapper for (viem.getLogs)[https://viem.sh/docs/actions/public/getLogs#getlogs].
109
+ * Accepts `eventName` and `eventNames` as optional parameters to narrow the returned log types.
110
+ * @example
111
+ * ```ts
112
+ * const logs = contract.getLogs({ eventName: 'EventName' })
113
+ * const logs = contract.getLogs({ eventNames: ['EventName'] })
114
+ *
115
+ * @public
116
+ * @async
117
+ * @template {ContractEvent} event
118
+ * @template {ExtractAbiEvent<
119
+ * ContractAbi,
120
+ * event
121
+ * >} [abiEvent=ExtractAbiEvent<ContractAbi, event>]
122
+ * @param {?Omit<
123
+ * GetLogsParams<ContractAbi, event, abiEvent, abiEvent[]>,
124
+ * 'event' | 'events'
125
+ * > & {
126
+ * eventName?: event;
127
+ * eventNames?: event[];
128
+ * }} [params]
129
+ * @returns {Promise<GetLogsReturnType<abiEvent, abiEvent[]>>}
130
+ */
131
+ public async getLogs<
132
+ event extends ContractEventName<ContractAbi>,
133
+ const abiEvent extends ExtractAbiEvent<
134
+ ContractAbi,
135
+ event
136
+ > = ExtractAbiEvent<ContractAbi, event>,
137
+ >(
138
+ params?: Omit<
139
+ GetLogsParams<ContractAbi, event, abiEvent, abiEvent[]>,
140
+ 'event' | 'events'
141
+ > & {
142
+ eventName?: event;
143
+ eventNames?: event[];
144
+ },
145
+ ): Promise<GetLogsReturnType<abiEvent, abiEvent[]>> {
146
+ return getLogs(this._config.getClient({ chainId: params?.chainId }), {
147
+ // biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wag
148
+ ...(params as any),
149
+ ...(params?.eventName
150
+ ? {
151
+ event: getAbiItem({
152
+ abi: this.abi,
153
+ name: params.eventName,
154
+ // biome-ignore lint/suspicious/noExplicitAny: awkward abi intersection issue
155
+ } as any),
156
+ }
157
+ : {}),
158
+ ...(params?.eventNames
159
+ ? {
160
+ events: params.eventNames.map((name) =>
161
+ getAbiItem({
162
+ abi: this.abi,
163
+ name,
164
+ // biome-ignore lint/suspicious/noExplicitAny: awkward abi intersection issue
165
+ } as any),
166
+ ),
167
+ }
168
+ : {}),
169
+ address: this.assertValidAddress(),
170
+ });
171
+ }
172
+
173
+ /**
174
+ * A typed wrapper for `wagmi.watchContractEvent`
175
+ *
176
+ * @public
177
+ * @template {ContractEvent} event
178
+ * @param {(
179
+ * log: WatchContractEventOnLogsParameter<ContractAbi, event, true>[number],
180
+ * ) => unknown} cb
181
+ * @param {?WatchParams<ContractAbi, event> & {
182
+ * eventName?: event;
183
+ * }} [params]
184
+ * @returns {() => void}
185
+ */
186
+ public subscribe<event extends ContractEventName<ContractAbi>>(
187
+ cb: (
188
+ log: WatchContractEventOnLogsParameter<ContractAbi, event, true>[number],
189
+ ) => unknown,
190
+ params?: WatchParams<ContractAbi, event> & {
191
+ eventName?: event;
192
+ },
193
+ ) {
194
+ return watchContractEvent<
195
+ typeof this._config,
196
+ (typeof this._config)['chains'][number]['id'],
197
+ ContractAbi,
198
+ event
199
+ >(this._config, {
200
+ // biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
201
+ ...(params as any),
202
+ eventName: params?.eventName,
203
+ abi: this.abi,
204
+ address: this.assertValidAddress(),
205
+ onLogs: (logs) => {
206
+ for (let l of logs) {
207
+ cb(l);
208
+ }
209
+ },
210
+ });
211
+ }
212
+
213
+ /**
214
+ * @see {@link awaitResult}
215
+ * @protected
216
+ * @async
217
+ * @template [Result=unknown]
218
+ * @param {Promise<HashAndSimulatedResult<Result>>} hashPromise
219
+ * @param {?Omit<WaitForTransactionReceiptParameters, 'hash'>} [waitParams]
220
+ * @returns {Promise<Result>}
221
+ */
222
+ protected async awaitResult<Result = unknown>(
223
+ hashPromise: Promise<HashAndSimulatedResult<Result>>,
224
+ waitParams?: Omit<WaitForTransactionReceiptParameters, 'hash'>,
225
+ ) {
226
+ return await awaitResult(this._config, hashPromise, waitParams);
227
+ }
228
+ }
@@ -0,0 +1,250 @@
1
+ import { type Config, deployContract } from '@wagmi/core';
2
+ import type {
3
+ Abi,
4
+ Account,
5
+ Address,
6
+ ContractEventName,
7
+ Hash,
8
+ Hex,
9
+ WaitForTransactionReceiptParameters,
10
+ } from 'viem';
11
+ import {
12
+ DeployableAlreadyDeployedError,
13
+ DeployableBuildParametersUnspecifiedError,
14
+ DeployableMissingPayloadError,
15
+ DeployableWagmiConfigurationRequiredError,
16
+ } from '../errors';
17
+ import { getDeployedContractAddress } from '../utils';
18
+ import { Contract } from './Contract';
19
+
20
+ /**
21
+ * A base class representing a deployable contract, contains base implementations for deployment and initialization payload construction.
22
+ *
23
+ * @export
24
+ * @typedef {GenericDeployableParams}
25
+ */
26
+ export type GenericDeployableParams = Omit<
27
+ Parameters<typeof deployContract>[1],
28
+ 'args' | 'account'
29
+ > & {
30
+ args: [Hex, ...Array<Hex>];
31
+ account?: Account;
32
+ };
33
+
34
+ /**
35
+ * A generic type that encapsulates either an initialization payload for a contract, or a valid address for a previously deployed contract.
36
+ *
37
+ * @export
38
+ * @typedef {DeployablePayloadOrAddress}
39
+ * @template [Payload=unknown]
40
+ */
41
+ export type DeployablePayloadOrAddress<Payload = unknown> = Payload | Address;
42
+
43
+ /**
44
+ * Instantion options for the base deployable.
45
+ *
46
+ * @export
47
+ * @interface DeployableOptions
48
+ * @typedef {DeployableOptions}
49
+ */
50
+ export interface DeployableOptions {
51
+ /**
52
+ * [Wagmi Configuration](https://wagmi.sh/core/api/createConfig)
53
+ *
54
+ * @see {@link Config}
55
+ * @type {Config}
56
+ */
57
+ config: Config;
58
+ /**
59
+ * [Viem Local Account](https://viem.sh/docs/accounts/local), required if in a Node environment
60
+ *
61
+ * @see {@link Account}
62
+ * @type {?Account}
63
+ */
64
+ account?: Account;
65
+ }
66
+
67
+ /**
68
+ * A generic deployable contract that encapsulates common operations related to contract deployment
69
+ *
70
+ * @export
71
+ * @class Deployable
72
+ * @typedef {Deployable}
73
+ * @template [Payload=unknown]
74
+ * @template {Abi} [ContractAbi=[]]
75
+ * @template {ContractEventName<ContractAbi>} [ContractEvent=ContractEventName<ContractAbi>]
76
+ * @extends {Contract<ContractAbi, ContractEvent>}
77
+ */
78
+ export class Deployable<
79
+ Payload,
80
+ ContractAbi extends Abi,
81
+ > extends Contract<ContractAbi> {
82
+ /**
83
+ * The deployable payload used either for contract construction or initialization
84
+ *
85
+ * @protected
86
+ * @type {(Payload | undefined)}
87
+ */
88
+ protected _payload: Payload | undefined;
89
+ /**
90
+ * If it exists, [Viem Local Account](https://viem.sh/docs/accounts/local), if in a Node environment
91
+ *
92
+ * @protected
93
+ * @type {?Account}
94
+ */
95
+ protected _account?: Account;
96
+
97
+ /**
98
+ * Creates an instance of Deployable.
99
+ *
100
+ * @constructor
101
+ * @param {DeployableOptions} param0
102
+ * @param {?Account} [param0.account]
103
+ * @param {Config} param0.config
104
+ * @param {DeployablePayloadOrAddress<Payload>} payload
105
+ */
106
+ constructor(
107
+ { account, config }: DeployableOptions,
108
+ payload?: DeployablePayloadOrAddress<Payload>,
109
+ ) {
110
+ if (typeof payload === 'string') {
111
+ super(config, payload as Address);
112
+ } else {
113
+ super(config, undefined);
114
+ this._payload = payload as Payload;
115
+ }
116
+ if (account) this._account = account;
117
+ }
118
+
119
+ /**
120
+ * Returns the attached deployable payload, if it exists
121
+ *
122
+ * @readonly
123
+ * @type {Payload}
124
+ */
125
+ get payload() {
126
+ return this._payload;
127
+ }
128
+
129
+ /**
130
+ * Attaches a new payload for use with this deployable's initialization
131
+ *
132
+ * @public
133
+ * @param {Payload} payload
134
+ * @returns {this}
135
+ */
136
+ public withPayload(payload: Payload) {
137
+ this._payload = payload;
138
+ return this;
139
+ }
140
+
141
+ /**
142
+ * High level deployment function to deploy and await the contract address.
143
+ * This is mainly a convenience method to easily deploy a contract, but will not initialize a `Cloneable`,
144
+ * which makes it useless for Boost components.
145
+ * Obviously you can ignore the TS warnings and use this, but you shouldn't in most all cases.
146
+ *
147
+ * @public
148
+ * @async
149
+ * @param {?Payload} [_payload]
150
+ * @param {?DeployableOptions} [_options]
151
+ * @param {?Omit<WaitForTransactionReceiptParameters, 'hash'>} [waitParams] - See [viem.WaitForTransactionReceipt](https://v1.viem.sh/docs/actions/public/waitForTransactionReceipt.html#waitfortransactionreceipt)
152
+ * @returns {Promise<this>}
153
+ */
154
+ protected async deploy(
155
+ _payload?: Payload,
156
+ _options?: DeployableOptions,
157
+ waitParams?: Omit<WaitForTransactionReceiptParameters, 'hash'>,
158
+ ) {
159
+ const config = _options?.config || this._config;
160
+ const address = await getDeployedContractAddress(
161
+ config,
162
+ this.deployRaw(_payload, _options),
163
+ waitParams,
164
+ );
165
+ this._address = address;
166
+ return this;
167
+ }
168
+
169
+ /**
170
+ * The lower level contract deployment function that does not await for the transaction receipt.
171
+ * This is mainly a convenience method to easily deploy a contract, but will not initialize a `Cloneable`,
172
+ * which makes it useless for Boost components.
173
+ * Obviously you can ignore the TS warnings and use this, but you shouldn't in most all cases.
174
+ *
175
+ * @public
176
+ * @async
177
+ * @param {?Payload} [_payload]
178
+ * @param {?DeployableOptions} [_options]
179
+ * @returns {Promise<Hash>}
180
+ * @throws {@link DeployableAlreadyDeployedError}
181
+ * @throws {@link DeployableWagmiConfigurationRequiredError}
182
+ * @throws {@link DeployableMissingPayloadError}
183
+ */
184
+ protected async deployRaw(
185
+ _payload?: Payload,
186
+ _options?: DeployableOptions,
187
+ ): Promise<Hash> {
188
+ if (this.address) throw new DeployableAlreadyDeployedError(this.address);
189
+ const [payload, options] = this.validateDeploymentConfig(
190
+ _payload,
191
+ _options,
192
+ );
193
+ return await deployContract(options.config, {
194
+ ...this.buildParameters(payload),
195
+ ...this.optionallyAttachAccount(options.account),
196
+ });
197
+ }
198
+
199
+ /**
200
+ * Internal function to attach the connected account to write methods to avoid manually passing in an account each call.
201
+ *
202
+ * @protected
203
+ * @param {?Account} [account]
204
+ * @returns {({ account: Account; } | { account?: undefined; })}
205
+ */
206
+ protected optionallyAttachAccount(account?: Account) {
207
+ if (account) return { account };
208
+ return this._account ? { account: this._account } : {};
209
+ }
210
+
211
+ /**
212
+ * Base parameter constructor, should return a partial `viem.deployContract` parameters shape including abi, bytecode, and arguments, if any.
213
+ * Expected to be overridden by protocol contracts.
214
+ *
215
+ * @public
216
+ * @param {?Payload} [_payload]
217
+ * @param {?DeployableOptions} [_options]
218
+ * @returns {GenericDeployableParams}
219
+ */
220
+ public buildParameters(
221
+ _payload?: Payload,
222
+ _options?: DeployableOptions,
223
+ ): GenericDeployableParams {
224
+ throw new DeployableBuildParametersUnspecifiedError();
225
+ }
226
+
227
+ /**
228
+ * Internal method used to ensure that a Wagmi configuration and payload are always present when deploying.
229
+ *
230
+ * @protected
231
+ * @template [P=Payload]
232
+ * @param {?P} [_payload]
233
+ * @param {?DeployableOptions} [_options]
234
+ * @returns {[P, DeployableOptions]}
235
+ * @throws {@link DeployableWagmiConfigurationRequiredError}
236
+ * @throws {@link DeployableMissingPayloadError}
237
+ */
238
+ protected validateDeploymentConfig<P = Payload>(
239
+ _payload?: P,
240
+ _options?: DeployableOptions,
241
+ ) {
242
+ const options = _options || {
243
+ config: this._config,
244
+ account: this._account,
245
+ };
246
+ if (!options) throw new DeployableWagmiConfigurationRequiredError();
247
+ const payload = _payload || this._payload;
248
+ return [payload, options] as [P, DeployableOptions];
249
+ }
250
+ }
@@ -0,0 +1,234 @@
1
+ import {
2
+ type aCloneableAbi,
3
+ readACloneableGetComponentInterface,
4
+ readACloneableSupportsInterface,
5
+ } from '@boostxyz/evm';
6
+ import { deployContract } from '@wagmi/core';
7
+ import {
8
+ type Abi,
9
+ type Address,
10
+ type Hash,
11
+ type Hex,
12
+ type WaitForTransactionReceiptParameters,
13
+ isAddress,
14
+ isAddressEqual,
15
+ zeroAddress,
16
+ } from 'viem';
17
+ import {
18
+ DeployableAlreadyDeployedError,
19
+ DeployableMissingPayloadError,
20
+ } from '../errors';
21
+ import { type ReadParams, RegistryType } from '../utils';
22
+ import {
23
+ Deployable,
24
+ type DeployableOptions,
25
+ type DeployablePayloadOrAddress,
26
+ } from './Deployable';
27
+
28
+ /**
29
+ * A base class representing a generic base Boost Protocol target contract, extended by Actions, AllowLists, Budgets, Incentives, and Validators.
30
+ *
31
+ * @export
32
+ * @class DeployableTarget
33
+ * @typedef {DeployableTarget}
34
+ * @template [Payload=unknown]
35
+ * @extends {Deployable<Payload>}
36
+ */
37
+ export class DeployableTarget<
38
+ Payload,
39
+ ContractAbi extends Abi,
40
+ > extends Deployable<Payload, ContractAbi> {
41
+ /**
42
+ * A static property representing a map of stringified chain ID's to the address of the base implementation on chain, used when cloning base contracts.
43
+ *
44
+ * @static
45
+ * @readonly
46
+ * @type {Record<string, Address>}
47
+ */
48
+ static readonly bases: Record<number, Address> = {};
49
+ /**
50
+ * The target's registry type.
51
+ *
52
+ * @static
53
+ * @readonly
54
+ * @type {RegistryType}
55
+ */
56
+ static readonly registryType: RegistryType = RegistryType.ACTION;
57
+ /**
58
+ * A property asserting that the protocol should eiher clone and initialize a new target from the base implementation, or re-use an existing contract without initializing.
59
+ *
60
+ * @readonly
61
+ * @type {boolean}
62
+ */
63
+ readonly _isBase: boolean = true;
64
+ public get isBase() {
65
+ if (
66
+ !!this.address &&
67
+ Object.values(this.bases).some((base) =>
68
+ // biome-ignore lint/style/noNonNullAssertion: won't evaluate this if address checked and defined above
69
+ isAddressEqual(this.address!, base),
70
+ )
71
+ )
72
+ return true;
73
+ return this._isBase;
74
+ }
75
+
76
+ /**
77
+ * Creates an instance of DeployableTarget.
78
+ *
79
+ * @constructor
80
+ * @param {DeployableOptions} options
81
+ * @param {DeployablePayloadOrAddress<Payload>} payload - Either a given implementation's initialization payload, or an address to an existing on chain target.
82
+ * @param {?boolean} [isBase] - A property asserting that the protocol should eiher clone and initialize a new target from the base implementation, or re-use an existing contract without initializing.
83
+ */
84
+ constructor(
85
+ options: DeployableOptions,
86
+ payload?: DeployablePayloadOrAddress<Payload>,
87
+ isBase?: boolean,
88
+ ) {
89
+ super(options, payload);
90
+ // if supplying a custom address, safe enough to assume it is not a base address which makes reusing contracts like budgets easier
91
+ if (
92
+ typeof payload === 'string' &&
93
+ isAddress(payload) &&
94
+ payload !== zeroAddress &&
95
+ !Object.values(this.bases).some((base) => {
96
+ if (!payload || !base) return false;
97
+ return isAddressEqual(payload, base);
98
+ })
99
+ )
100
+ isBase = false;
101
+ if (isBase !== undefined) this._isBase = isBase;
102
+ }
103
+
104
+ /**
105
+ * A getter that will return the base implementation's static addresses by numerical chain ID
106
+ *
107
+ * @public
108
+ * @readonly
109
+ * @type {Record<number, Address>}
110
+ */
111
+ public get bases(): Record<number, Address> {
112
+ return (this.constructor as typeof DeployableTarget).bases;
113
+ }
114
+
115
+ /**
116
+ * A getter that returns the registry type of the base implementation
117
+ *
118
+ * @public
119
+ * @readonly
120
+ * @type {RegistryType}
121
+ */
122
+ public get registryType(): RegistryType {
123
+ return (this.constructor as typeof DeployableTarget).registryType;
124
+ }
125
+
126
+ /**
127
+ * @inheritdoc
128
+ *
129
+ * @public
130
+ * @async
131
+ * @param {?Payload} [payload]
132
+ * @param {?DeployableOptions} [options]
133
+ * @param {?Omit<WaitForTransactionReceiptParameters, 'hash'>} [waitParams]
134
+ * @returns {Promise<this>}
135
+ */
136
+ protected override async deploy(
137
+ payload?: Payload,
138
+ options?: DeployableOptions,
139
+ waitParams?: Omit<WaitForTransactionReceiptParameters, 'hash'>,
140
+ ) {
141
+ await super.deploy(payload, options, waitParams);
142
+ this.assertValidAddress();
143
+ return this;
144
+ }
145
+
146
+ /**
147
+ * @inheritdoc
148
+ *
149
+ * @public
150
+ * @async
151
+ * @param {?Payload} [_payload]
152
+ * @param {?DeployableOptions} [_options]
153
+ * @returns {Promise<Hash>}
154
+ */
155
+ protected override async deployRaw(
156
+ _payload?: Payload,
157
+ _options?: DeployableOptions,
158
+ ): Promise<Hash> {
159
+ if (this.address) throw new DeployableAlreadyDeployedError(this.address);
160
+ const payload = _payload || this._payload;
161
+ const config = _options?.config || this._config;
162
+ const { args, ...deployment } = this.buildParameters(payload);
163
+ return await deployContract(config, {
164
+ ...deployment,
165
+ ...this.optionallyAttachAccount(_options?.account),
166
+ // Deployable targets don't construct with arguments, they initialize with encoded payloads
167
+ args: [],
168
+ });
169
+ }
170
+
171
+ /**
172
+ * Check if the contract supports the given interface
173
+ *
174
+ * @public
175
+ * @async
176
+ * @param {Hex} interfaceId - The interface identifier
177
+ * @param {?ReadParams} [params]
178
+ * @returns {Promise<boolean>} - True if the contract supports the interface
179
+ */
180
+ public async supportsInterface(
181
+ interfaceId: Hex,
182
+ params?: ReadParams<typeof aCloneableAbi, 'supportsInterface'>,
183
+ ) {
184
+ return await readACloneableSupportsInterface(this._config, {
185
+ address: this.assertValidAddress(),
186
+ ...this.optionallyAttachAccount(),
187
+ // biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
188
+ ...(params as any),
189
+ args: [interfaceId],
190
+ });
191
+ }
192
+
193
+ /**
194
+ * Return a cloneable's unique identifier for downstream consumers to differentiate various targets
195
+ * All implementations must override this function
196
+ *
197
+ * @public
198
+ * @async
199
+ * @param {?ReadParams} [params]
200
+ * @returns {Promise<Hex>}
201
+ */
202
+ public async getComponentInterface(
203
+ params?: ReadParams<typeof aCloneableAbi, 'getComponentInterface'>,
204
+ ) {
205
+ return await readACloneableGetComponentInterface(this._config, {
206
+ address: this.assertValidAddress(),
207
+ ...this.optionallyAttachAccount(),
208
+ // biome-ignore lint/suspicious/noExplicitAny: Accept any shape of valid wagmi/viem parameters, wagmi does the same thing internally
209
+ ...(params as any),
210
+ args: [],
211
+ });
212
+ }
213
+
214
+ /**
215
+ * @inheritdoc
216
+ *
217
+ * @protected
218
+ * @template [P=Payload]
219
+ * @param {?P} [_payload]
220
+ * @param {?DeployableOptions} [_options]
221
+ * @returns {[P, DeployableOptions]}
222
+ */
223
+ protected override validateDeploymentConfig<P = Payload>(
224
+ _payload?: P,
225
+ _options?: DeployableOptions,
226
+ ) {
227
+ const payload = _payload || this._payload;
228
+ if (!payload) throw new DeployableMissingPayloadError();
229
+ return super.validateDeploymentConfig(payload, _options) as [
230
+ P,
231
+ DeployableOptions,
232
+ ];
233
+ }
234
+ }