@zoralabs/protocol-sdk 0.3.4 → 0.4.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/.turbo/turbo-build.log +6 -6
- package/CHANGELOG.md +34 -0
- package/README.md +30 -58
- package/dist/anvil.d.ts +4 -2
- package/dist/anvil.d.ts.map +1 -1
- package/dist/constants.d.ts +32 -0
- package/dist/constants.d.ts.map +1 -1
- package/dist/index.cjs +819 -518
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +788 -493
- package/dist/index.js.map +1 -1
- package/dist/mint/mint-api-client.d.ts +16 -216
- package/dist/mint/mint-api-client.d.ts.map +1 -1
- package/dist/mint/mint-client.d.ts +7 -227
- package/dist/mint/mint-client.d.ts.map +1 -1
- package/dist/premint/contract-types.d.ts +125 -0
- package/dist/premint/contract-types.d.ts.map +1 -0
- package/dist/premint/premint-api-client.d.ts +14 -7
- package/dist/premint/premint-api-client.d.ts.map +1 -1
- package/dist/premint/premint-client.d.ts +45 -115
- package/dist/premint/premint-client.d.ts.map +1 -1
- package/dist/premint/preminter.d.ts +102 -21
- package/dist/premint/preminter.d.ts.map +1 -1
- package/dist/types.d.ts +2 -0
- package/dist/types.d.ts.map +1 -0
- package/package.json +1 -1
- package/src/anvil.ts +7 -4
- package/src/constants.ts +7 -0
- package/src/index.ts +2 -0
- package/src/mint/mint-api-client.ts +72 -68
- package/src/mint/mint-client.test.ts +9 -11
- package/src/mint/mint-client.ts +51 -221
- package/src/premint/contract-types.ts +109 -0
- package/src/premint/premint-api-client.ts +162 -22
- package/src/premint/premint-client.test.ts +186 -84
- package/src/premint/premint-client.ts +357 -289
- package/src/premint/preminter.test.ts +209 -130
- package/src/premint/preminter.ts +377 -54
- package/src/types.ts +1 -0
- package/dist/apis/generated/discover-api-types.d.ts +0 -2131
- package/dist/apis/generated/discover-api-types.d.ts.map +0 -1
- package/src/apis/generated/discover-api-types.ts +0 -2180
package/src/premint/preminter.ts
CHANGED
|
@@ -1,72 +1,395 @@
|
|
|
1
1
|
import { Address } from "abitype";
|
|
2
|
-
import {
|
|
3
|
-
|
|
4
|
-
|
|
2
|
+
import {
|
|
3
|
+
zoraCreator1155PremintExecutorImplABI as preminterAbi,
|
|
4
|
+
zoraCreator1155ImplABI,
|
|
5
|
+
zoraCreator1155PremintExecutorImplABI,
|
|
6
|
+
zoraCreator1155PremintExecutorImplAddress,
|
|
7
|
+
} from "@zoralabs/protocol-deployments";
|
|
8
|
+
import {
|
|
9
|
+
TypedDataDefinition,
|
|
10
|
+
recoverTypedDataAddress,
|
|
11
|
+
Hex,
|
|
12
|
+
PublicClient,
|
|
13
|
+
zeroAddress,
|
|
14
|
+
hashDomain,
|
|
15
|
+
keccak256,
|
|
16
|
+
concat,
|
|
17
|
+
recoverAddress,
|
|
18
|
+
GetEventArgs,
|
|
19
|
+
} from "viem";
|
|
20
|
+
import {
|
|
21
|
+
ContractCreationConfig,
|
|
22
|
+
PremintConfig,
|
|
23
|
+
PremintConfigForTokenCreationConfig,
|
|
24
|
+
PremintConfigV1,
|
|
25
|
+
PremintConfigV2,
|
|
26
|
+
PremintConfigVersion,
|
|
27
|
+
PremintConfigWithVersion,
|
|
28
|
+
PreminterDomain,
|
|
29
|
+
TokenCreationConfig,
|
|
30
|
+
v1Types,
|
|
31
|
+
v2Types,
|
|
32
|
+
} from "./contract-types";
|
|
5
33
|
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
"premint"
|
|
9
|
-
>["inputs"];
|
|
34
|
+
export const getPremintExecutorAddress = () =>
|
|
35
|
+
zoraCreator1155PremintExecutorImplAddress[999];
|
|
10
36
|
|
|
11
|
-
|
|
37
|
+
/**
|
|
38
|
+
* Creates a typed data definition for a premint config. Works for all versions of the premint config by specifying the premintConfigVersion.
|
|
39
|
+
*
|
|
40
|
+
* @param params.verifyingContract the address of the 1155 contract
|
|
41
|
+
* @param params.chainId the chain id the premint is signed for
|
|
42
|
+
* @param params.premintConfigVersion the version of the premint config
|
|
43
|
+
* @param params.premintConfig the premint config
|
|
44
|
+
* @returns
|
|
45
|
+
*/
|
|
46
|
+
export const premintTypedDataDefinition = <T extends PremintConfigVersion>({
|
|
47
|
+
verifyingContract,
|
|
48
|
+
chainId,
|
|
49
|
+
premintConfigVersion: version,
|
|
50
|
+
premintConfig,
|
|
51
|
+
}: {
|
|
52
|
+
verifyingContract: Address;
|
|
53
|
+
chainId: number;
|
|
54
|
+
} & PremintConfigWithVersion<T>): TypedDataDefinition => {
|
|
55
|
+
const domain = {
|
|
56
|
+
chainId,
|
|
57
|
+
name: PreminterDomain,
|
|
58
|
+
version,
|
|
59
|
+
verifyingContract: verifyingContract,
|
|
60
|
+
};
|
|
12
61
|
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
62
|
+
if (version === PremintConfigVersion.V1)
|
|
63
|
+
return {
|
|
64
|
+
domain,
|
|
65
|
+
types: v1Types,
|
|
66
|
+
message: premintConfig as PremintConfigV1,
|
|
67
|
+
primaryType: "CreatorAttribution",
|
|
68
|
+
} satisfies TypedDataDefinition<typeof v1Types, "CreatorAttribution">;
|
|
69
|
+
if (version === PremintConfigVersion.V2) {
|
|
70
|
+
return {
|
|
71
|
+
domain,
|
|
72
|
+
types: v2Types,
|
|
73
|
+
message: premintConfig as PremintConfigV2,
|
|
74
|
+
primaryType: "CreatorAttribution",
|
|
75
|
+
} satisfies TypedDataDefinition<typeof v2Types, "CreatorAttribution">;
|
|
76
|
+
}
|
|
16
77
|
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
78
|
+
throw new Error(`Invalid version ${version}`);
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
export type IsValidSignatureReturn = {
|
|
82
|
+
isAuthorized: boolean;
|
|
83
|
+
recoveredAddress?: Address;
|
|
84
|
+
};
|
|
85
|
+
|
|
86
|
+
export async function isAuthorizedToCreatePremint<
|
|
87
|
+
T extends PremintConfigVersion,
|
|
88
|
+
>({
|
|
89
|
+
collection,
|
|
90
|
+
collectionAddress,
|
|
91
|
+
publicClient,
|
|
21
92
|
premintConfig,
|
|
22
|
-
|
|
93
|
+
premintConfigVersion,
|
|
94
|
+
signature,
|
|
95
|
+
signer,
|
|
23
96
|
}: {
|
|
97
|
+
collection: ContractCreationConfig;
|
|
98
|
+
collectionAddress: Address;
|
|
99
|
+
publicClient: PublicClient;
|
|
100
|
+
signature: Hex;
|
|
101
|
+
signer: Address;
|
|
102
|
+
} & PremintConfigWithVersion<T>) {
|
|
103
|
+
// if we are using legacy version of premint config, we can use the function
|
|
104
|
+
// "isValidSignature" which we know exists on the premint executor contract
|
|
105
|
+
if (premintConfigVersion === PremintConfigVersion.V1) {
|
|
106
|
+
const [isValidSignature] = await publicClient.readContract({
|
|
107
|
+
abi: zoraCreator1155PremintExecutorImplABI,
|
|
108
|
+
address: getPremintExecutorAddress(),
|
|
109
|
+
functionName: "isValidSignature",
|
|
110
|
+
args: [collection, premintConfig as PremintConfigV1, signature],
|
|
111
|
+
});
|
|
112
|
+
|
|
113
|
+
return isValidSignature;
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
// otherwize, we must assume the newer version of premint executor is deployed, so we call that.
|
|
117
|
+
return await publicClient.readContract({
|
|
118
|
+
abi: preminterAbi,
|
|
119
|
+
address: getPremintExecutorAddress(),
|
|
120
|
+
functionName: "isAuthorizedToCreatePremint",
|
|
121
|
+
args: [signer, collection.contractAdmin, collectionAddress],
|
|
122
|
+
});
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
export async function recoverPremintSigner<T extends PremintConfigVersion>({
|
|
126
|
+
signature,
|
|
127
|
+
...rest
|
|
128
|
+
}: {
|
|
129
|
+
signature: Hex;
|
|
130
|
+
chainId: number;
|
|
24
131
|
verifyingContract: Address;
|
|
25
|
-
|
|
132
|
+
} & PremintConfigWithVersion<T>): Promise<Address> {
|
|
133
|
+
const typedData = premintTypedDataDefinition(rest);
|
|
134
|
+
return await recoverTypedDataAddress({
|
|
135
|
+
...typedData,
|
|
136
|
+
signature,
|
|
137
|
+
});
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
export async function tryRecoverPremintSigner(
|
|
141
|
+
params: Parameters<typeof recoverPremintSigner>[0],
|
|
142
|
+
) {
|
|
143
|
+
try {
|
|
144
|
+
return await recoverPremintSigner(params);
|
|
145
|
+
} catch (error) {
|
|
146
|
+
console.error(error);
|
|
147
|
+
return undefined;
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
/**
|
|
152
|
+
* Recovers the address from a typed data signature and then checks if the recovered address is authorized to create a premint
|
|
153
|
+
*
|
|
154
|
+
* @param params validationProperties
|
|
155
|
+
* @param params.typedData typed data definition for premint config
|
|
156
|
+
* @param params.signature signature to validate
|
|
157
|
+
* @param params.publicClient public rpc read-only client
|
|
158
|
+
* @param params.premintConfigContractAdmin the original contractAdmin on the ContractCreationConfig for the premint; this is usually the original creator of the premint
|
|
159
|
+
* @param params.tokenContract the address of the 1155 contract
|
|
160
|
+
* @returns
|
|
161
|
+
*/
|
|
162
|
+
export async function isValidSignature<T extends PremintConfigVersion>({
|
|
163
|
+
signature,
|
|
164
|
+
publicClient,
|
|
165
|
+
collection,
|
|
166
|
+
chainId,
|
|
167
|
+
...premintConfigAndVersion
|
|
168
|
+
}: {
|
|
169
|
+
collection: ContractCreationConfig;
|
|
170
|
+
signature: Hex;
|
|
26
171
|
chainId: number;
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
const
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
172
|
+
publicClient: PublicClient;
|
|
173
|
+
} & PremintConfigWithVersion<T>): Promise<IsValidSignatureReturn> {
|
|
174
|
+
const tokenContract = await getPremintCollectionAddress({
|
|
175
|
+
collection,
|
|
176
|
+
publicClient,
|
|
177
|
+
});
|
|
178
|
+
const recoveredAddress = await tryRecoverPremintSigner({
|
|
179
|
+
...premintConfigAndVersion,
|
|
180
|
+
signature,
|
|
181
|
+
verifyingContract: tokenContract,
|
|
182
|
+
chainId,
|
|
183
|
+
});
|
|
184
|
+
|
|
185
|
+
if (!recoverAddress) {
|
|
186
|
+
return {
|
|
187
|
+
isAuthorized: false,
|
|
188
|
+
};
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
const isAuthorized = await isAuthorizedToCreatePremint({
|
|
192
|
+
signer: recoveredAddress!,
|
|
193
|
+
collection,
|
|
194
|
+
collectionAddress: tokenContract,
|
|
195
|
+
publicClient,
|
|
196
|
+
signature,
|
|
197
|
+
...premintConfigAndVersion,
|
|
198
|
+
});
|
|
199
|
+
|
|
200
|
+
return {
|
|
201
|
+
isAuthorized,
|
|
202
|
+
recoveredAddress,
|
|
52
203
|
};
|
|
204
|
+
}
|
|
53
205
|
|
|
54
|
-
|
|
206
|
+
/**
|
|
207
|
+
* Converts a premint config from v1 to v2
|
|
208
|
+
*
|
|
209
|
+
* @param premintConfig premint config to convert
|
|
210
|
+
* @param createReferral address that referred the creator, that will receive create referral rewards for the created token
|
|
211
|
+
*/
|
|
212
|
+
export function migratePremintConfigToV2({
|
|
213
|
+
premintConfig,
|
|
214
|
+
createReferral = zeroAddress,
|
|
215
|
+
}: {
|
|
216
|
+
premintConfig: PremintConfigV1;
|
|
217
|
+
createReferral: Address;
|
|
218
|
+
}): PremintConfigV2 {
|
|
219
|
+
return {
|
|
220
|
+
...premintConfig,
|
|
221
|
+
tokenConfig: {
|
|
222
|
+
tokenURI: premintConfig.tokenConfig.tokenURI,
|
|
223
|
+
maxSupply: premintConfig.tokenConfig.maxSupply,
|
|
224
|
+
maxTokensPerAddress: premintConfig.tokenConfig.maxTokensPerAddress,
|
|
225
|
+
pricePerToken: premintConfig.tokenConfig.pricePerToken,
|
|
226
|
+
mintStart: premintConfig.tokenConfig.mintStart,
|
|
227
|
+
mintDuration: premintConfig.tokenConfig.mintDuration,
|
|
228
|
+
payoutRecipient: premintConfig.tokenConfig.royaltyRecipient,
|
|
229
|
+
royaltyBPS: premintConfig.tokenConfig.royaltyBPS,
|
|
230
|
+
fixedPriceMinter: premintConfig.tokenConfig.fixedPriceMinter,
|
|
231
|
+
createReferral,
|
|
232
|
+
},
|
|
233
|
+
};
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
export type CreatorAttributionEventParams = GetEventArgs<
|
|
237
|
+
typeof zoraCreator1155ImplABI,
|
|
238
|
+
"CreatorAttribution",
|
|
239
|
+
{ EnableUnion: false }
|
|
240
|
+
>;
|
|
241
|
+
|
|
242
|
+
/**
|
|
243
|
+
* Recovers the address from a CreatorAttribution event emitted from a ZoraCreator1155 contract
|
|
244
|
+
* Useful for verifying that the creator of a token is the one who signed a premint for its creation.
|
|
245
|
+
*
|
|
246
|
+
|
|
247
|
+
* @param creatorAttribution parameters from the CreatorAttribution event
|
|
248
|
+
* @param chainId the chain id of the current chain
|
|
249
|
+
* @param tokenContract the address of the 1155 contract
|
|
250
|
+
* @returns the address of the signer
|
|
251
|
+
*/
|
|
252
|
+
export const recoverCreatorFromCreatorAttribution = async ({
|
|
253
|
+
creatorAttribution: { version, domainName, structHash, signature },
|
|
254
|
+
chainId,
|
|
255
|
+
tokenContract,
|
|
256
|
+
}: {
|
|
257
|
+
creatorAttribution: CreatorAttributionEventParams;
|
|
258
|
+
tokenContract: Address;
|
|
259
|
+
chainId: number;
|
|
260
|
+
}) => {
|
|
261
|
+
// hash the eip712 domain based on the parameters emitted from the event:
|
|
262
|
+
const hashedDomain = hashDomain({
|
|
55
263
|
domain: {
|
|
56
264
|
chainId,
|
|
57
|
-
name:
|
|
58
|
-
|
|
59
|
-
verifyingContract: verifyingContract,
|
|
60
|
-
},
|
|
61
|
-
types,
|
|
62
|
-
message: {
|
|
63
|
-
tokenConfig,
|
|
64
|
-
uid,
|
|
265
|
+
name: domainName,
|
|
266
|
+
verifyingContract: tokenContract,
|
|
65
267
|
version,
|
|
66
|
-
deleted,
|
|
67
268
|
},
|
|
68
|
-
|
|
269
|
+
types: {
|
|
270
|
+
EIP712Domain: [
|
|
271
|
+
{ name: "name", type: "string" },
|
|
272
|
+
{ name: "version", type: "string" },
|
|
273
|
+
{
|
|
274
|
+
name: "chainId",
|
|
275
|
+
type: "uint256",
|
|
276
|
+
},
|
|
277
|
+
{
|
|
278
|
+
name: "verifyingContract",
|
|
279
|
+
type: "address",
|
|
280
|
+
},
|
|
281
|
+
],
|
|
282
|
+
},
|
|
283
|
+
});
|
|
284
|
+
|
|
285
|
+
// re-build the eip-712 typed data hash, consisting of the hashed domain and the structHash emitted from the event:
|
|
286
|
+
const parts: Hex[] = ["0x1901", hashedDomain, structHash!];
|
|
287
|
+
|
|
288
|
+
const hashedTypedData = keccak256(concat(parts));
|
|
289
|
+
|
|
290
|
+
return await recoverAddress({
|
|
291
|
+
hash: hashedTypedData,
|
|
292
|
+
signature: signature!,
|
|
293
|
+
});
|
|
294
|
+
};
|
|
295
|
+
|
|
296
|
+
export const supportedPremintVersions = async ({
|
|
297
|
+
tokenContract,
|
|
298
|
+
publicClient,
|
|
299
|
+
}: {
|
|
300
|
+
tokenContract: Address;
|
|
301
|
+
publicClient: PublicClient;
|
|
302
|
+
}): Promise<readonly string[]> => {
|
|
303
|
+
try {
|
|
304
|
+
return await publicClient.readContract({
|
|
305
|
+
abi: preminterAbi,
|
|
306
|
+
address: getPremintExecutorAddress(),
|
|
307
|
+
functionName: "supportedPremintSignatureVersions",
|
|
308
|
+
args: [tokenContract],
|
|
309
|
+
});
|
|
310
|
+
} catch (e) {
|
|
311
|
+
console.error(e);
|
|
312
|
+
// if the premint executor contract doesn't support the function, it must be v1
|
|
313
|
+
return ["1"];
|
|
314
|
+
}
|
|
315
|
+
};
|
|
316
|
+
/**
|
|
317
|
+
* Checks if the 1155 contract at that address supports the given version of the premint config.
|
|
318
|
+
*/
|
|
319
|
+
export const supportsPremintVersion = async ({
|
|
320
|
+
version,
|
|
321
|
+
tokenContract,
|
|
322
|
+
publicClient,
|
|
323
|
+
}: {
|
|
324
|
+
version: PremintConfigVersion;
|
|
325
|
+
tokenContract: Address;
|
|
326
|
+
publicClient: PublicClient;
|
|
327
|
+
}): Promise<boolean> => {
|
|
328
|
+
return (
|
|
329
|
+
await supportedPremintVersions({ tokenContract, publicClient })
|
|
330
|
+
).includes(version);
|
|
331
|
+
};
|
|
332
|
+
|
|
333
|
+
export async function getPremintCollectionAddress({
|
|
334
|
+
collection,
|
|
335
|
+
publicClient,
|
|
336
|
+
}: {
|
|
337
|
+
collection: ContractCreationConfig;
|
|
338
|
+
publicClient: PublicClient;
|
|
339
|
+
}): Promise<Address> {
|
|
340
|
+
return publicClient.readContract({
|
|
341
|
+
address: getPremintExecutorAddress(),
|
|
342
|
+
abi: zoraCreator1155PremintExecutorImplABI,
|
|
343
|
+
functionName: "getContractAddress",
|
|
344
|
+
args: [collection],
|
|
345
|
+
});
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
export function markPremintDeleted<T extends PremintConfig>(
|
|
349
|
+
premintConfig: T,
|
|
350
|
+
): T {
|
|
351
|
+
return {
|
|
352
|
+
...premintConfig,
|
|
353
|
+
version: premintConfig.version + 1,
|
|
354
|
+
deleted: true,
|
|
69
355
|
};
|
|
356
|
+
}
|
|
357
|
+
|
|
358
|
+
export function applyUpdateToPremint({
|
|
359
|
+
uid,
|
|
360
|
+
version,
|
|
361
|
+
tokenConfig,
|
|
362
|
+
tokenConfigUpdates,
|
|
363
|
+
}: {
|
|
364
|
+
tokenConfig: TokenCreationConfig;
|
|
365
|
+
tokenConfigUpdates: Partial<TokenCreationConfig>;
|
|
366
|
+
} & Pick<PremintConfig, "uid" | "version">): PremintConfig {
|
|
367
|
+
const updatedTokenConfig: TokenCreationConfig = {
|
|
368
|
+
...tokenConfig,
|
|
369
|
+
...tokenConfigUpdates,
|
|
370
|
+
} as const;
|
|
371
|
+
|
|
372
|
+
const result = {
|
|
373
|
+
deleted: false,
|
|
374
|
+
uid,
|
|
375
|
+
version: version + 1,
|
|
376
|
+
tokenConfig: updatedTokenConfig,
|
|
377
|
+
} as PremintConfig;
|
|
70
378
|
|
|
71
379
|
return result;
|
|
72
|
-
}
|
|
380
|
+
}
|
|
381
|
+
|
|
382
|
+
export function makeNewPremint<T extends TokenCreationConfig>({
|
|
383
|
+
tokenConfig,
|
|
384
|
+
uid,
|
|
385
|
+
}: {
|
|
386
|
+
tokenConfig: T;
|
|
387
|
+
uid: number;
|
|
388
|
+
}): PremintConfigForTokenCreationConfig<T> {
|
|
389
|
+
return {
|
|
390
|
+
deleted: false,
|
|
391
|
+
uid,
|
|
392
|
+
version: 0,
|
|
393
|
+
tokenConfig,
|
|
394
|
+
} as PremintConfigForTokenCreationConfig<T>;
|
|
395
|
+
}
|
package/src/types.ts
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export type GenericTokenIdTypes = number | bigint | string;
|