@@ -9,18 +9,24 @@ import {
99 TEST_ACCOUNT_B ,
1010 TEST_ACCOUNT_D ,
1111} from "../../../test/src/test-wallets.js" ;
12+ import { NATIVE_TOKEN_ADDRESS } from "../../constants/addresses.js" ;
1213import { resolveContractAbi } from "../../contract/actions/resolve-abi.js" ;
1314import { type ThirdwebContract , getContract } from "../../contract/contract.js" ;
1415import { sendAndConfirmTransaction } from "../../transaction/actions/send-and-confirm-transaction.js" ;
1516import { resolvePromisedValue } from "../../utils/promise/resolve-promised-value.js" ;
1617import { toEther } from "../../utils/units.js" ;
18+ import { generateMerkleTreeInfoERC1155 } from "../airdrop/write/merkleInfoERC1155.js" ;
19+ import { deployERC20Contract } from "../prebuilts/deploy-erc20.js" ;
1720import { deployERC1155Contract } from "../prebuilts/deploy-erc1155.js" ;
1821import { balanceOf } from "./__generated__/IERC1155/read/balanceOf.js" ;
22+ import { totalSupply } from "./__generated__/IERC1155/read/totalSupply.js" ;
1923import { nextTokenIdToMint } from "./__generated__/IERC1155Enumerable/read/nextTokenIdToMint.js" ;
24+ import { getActiveClaimCondition } from "./drops/read/getActiveClaimCondition.js" ;
2025import { getClaimConditions } from "./drops/read/getClaimConditions.js" ;
2126import { claimTo } from "./drops/write/claimTo.js" ;
2227import { resetClaimEligibility } from "./drops/write/resetClaimEligibility.js" ;
2328import { setClaimConditions } from "./drops/write/setClaimConditions.js" ;
29+ import { updateMetadata } from "./drops/write/updateMetadata.js" ;
2430import { getNFT } from "./read/getNFT.js" ;
2531import { isGetNFTsSupported } from "./read/getNFTs.js" ;
2632import { lazyMint } from "./write/lazyMint.js" ;
@@ -87,6 +93,20 @@ describe.runIf(process.env.TW_SECRET_KEY)(
8793 ` ) ;
8894 } ) ;
8995
96+ it ( "should update metadata" , async ( ) => {
97+ const updateTx = updateMetadata ( {
98+ contract,
99+ targetTokenId : 0n ,
100+ newMetadata : { name : "Test NFT 1" } ,
101+ } ) ;
102+ await sendAndConfirmTransaction ( {
103+ transaction : updateTx ,
104+ account : TEST_ACCOUNT_A ,
105+ } ) ;
106+ const token0 = await getNFT ( { contract, tokenId : 0n } ) ;
107+ expect ( token0 . metadata . name ) . toBe ( "Test NFT 1" ) ;
108+ } ) ;
109+
90110 it ( "should allow to claim tokens" , async ( ) => {
91111 await expect (
92112 balanceOf ( { contract, owner : TEST_ACCOUNT_A . address , tokenId : 0n } ) ,
@@ -409,5 +429,115 @@ describe.runIf(process.env.TW_SECRET_KEY)(
409429 . map ( ( f ) => toFunctionSelector ( f ) ) ;
410430 expect ( isGetNFTsSupported ( selectors ) ) . toBe ( true ) ;
411431 } ) ;
432+
433+ /**
434+ * This is to document the behavior where one can claim without paying if the claiming address
435+ * is the same as the PrimaryRecipientAddress, because of this Solidity code:
436+ * ```solidity
437+ * // CurrencyTransferLib.sol
438+ * function safeTransferERC20(address _currency, address _from, address _to, uint256 _amount) internal {
439+ * if (_from == _to) {
440+ * return;
441+ * }
442+ * ...
443+ * }
444+ * ```
445+ */
446+ it ( "address that is the same with PrimaryFeeRecipient can claim without paying ERC20" , async ( ) => {
447+ const tokenAddress = await deployERC20Contract ( {
448+ client : TEST_CLIENT ,
449+ chain : ANVIL_CHAIN ,
450+ account : TEST_ACCOUNT_A ,
451+ type : "TokenERC20" ,
452+ params : {
453+ name : "token20" ,
454+ contractURI : TEST_CONTRACT_URI ,
455+ } ,
456+ } ) ;
457+ const tokenId = 5n ;
458+ const setClaimTx = setClaimConditions ( {
459+ contract,
460+ tokenId,
461+ phases : [
462+ {
463+ maxClaimableSupply : 100n ,
464+ maxClaimablePerWallet : 100n ,
465+ currencyAddress : tokenAddress ,
466+ price : 1000 ,
467+ startTime : new Date ( ) ,
468+ } ,
469+ ] ,
470+ } ) ;
471+ await sendAndConfirmTransaction ( {
472+ transaction : setClaimTx ,
473+ account : TEST_ACCOUNT_A ,
474+ } ) ;
475+
476+ const transaction = claimTo ( {
477+ contract,
478+ tokenId,
479+ quantity : 50n ,
480+ to : TEST_ACCOUNT_A . address ,
481+ } ) ;
482+ await sendAndConfirmTransaction ( {
483+ transaction,
484+ account : TEST_ACCOUNT_A ,
485+ } ) ;
486+ const supplyCount = await totalSupply ( { contract, id : tokenId } ) ;
487+ expect ( supplyCount ) . toBe ( 50n ) ;
488+ } ) ;
489+
490+ it ( "getActiveClaimCondition should work" , async ( ) => {
491+ // Create a public allowlist claim phase
492+ const snapshot = [
493+ {
494+ recipient : TEST_ACCOUNT_B . address ,
495+ tokenId : 4 ,
496+ amount : 5 ,
497+ } ,
498+ {
499+ recipient : TEST_ACCOUNT_D . address ,
500+ tokenId : 4 ,
501+ amount : 5 ,
502+ } ,
503+ ] ;
504+
505+ const { merkleRoot } = await generateMerkleTreeInfoERC1155 ( {
506+ contract,
507+ tokenAddress : NATIVE_TOKEN_ADDRESS ,
508+ snapshot,
509+ } ) ;
510+
511+ const startTime = new Date ( ) ;
512+ const setCC = setClaimConditions ( {
513+ contract,
514+ tokenId : 4n ,
515+ phases : [
516+ {
517+ maxClaimableSupply : 100n ,
518+ maxClaimablePerWallet : 5n ,
519+ currencyAddress : NATIVE_TOKEN_ADDRESS ,
520+ price : 0.006 ,
521+ startTime,
522+ merkleRootHash : merkleRoot ,
523+ } ,
524+ ] ,
525+ } ) ;
526+
527+ await sendAndConfirmTransaction ( {
528+ transaction : setCC ,
529+ account : TEST_ACCOUNT_A ,
530+ } ) ;
531+
532+ const activeCC = await getActiveClaimCondition ( { contract, tokenId : 4n } ) ;
533+ expect ( activeCC . currency . toLowerCase ( ) ) . toBe (
534+ NATIVE_TOKEN_ADDRESS . toLowerCase ( ) ,
535+ ) ;
536+ expect ( activeCC . merkleRoot ) . toBe (
537+ "0x5baa4423af7125448ad7ca6913cdee7dd952a8d10a44f4fad4c50eea65c5c92d" ,
538+ ) ;
539+ expect ( activeCC . pricePerToken ) . toBe ( 6000000000000000n ) ;
540+ expect ( activeCC . quantityLimitPerWallet ) . toBe ( 5n ) ;
541+ } ) ;
412542 } ,
413543) ;
0 commit comments