Daniel

Posted on May 21, 2022Read on Mirror.xyz

人人都当科学家之免Gas体验mint爱死机

本文会详细讲解如何批量账号mint爱死机NFT以及原理。

因为无限mint已经不值手续费,故主要教学思路,无投资建议。

使用测试网模拟教学,小白用户可以无需任何Gas费用体验合约mint。

并无直接使用的脚本(需要脚本的可以去找一下用小狐狸直接mint,程序开源安全~)

读懂合约

官方爱死机NFT合约地址:

[https://etherscan.io/address/0xfd43d1da000558473822302e1d44d81da2e4cc0d#code]

首先合约是ERC1155,而不是常用NFT的ERC721合约,这两点有什么不同呢。ERC721也就是我们常说的NFT,非同质化代币,每一个代币都是独一无二的,可以有自己的属性特征等。而ERC1155则是既有非同质化代币也有同质化代币,每一个种类型的代币可以有与他相同的存在。具体举例说明,一个游戏中可以有很多种不同的装备,但是同样的装备也可以有很多件,那么这个场景就很适用于ERC1155。而爱死机的nft主要有9种,每一种可以有无数个,细心的同学会发现在opensea上面显示和购买的方式与其他绝大多数都会不一样,例如同一个nft会显示有多少人拥有,总量是多少等。因为是同质化的,每个人手上持有的相同的nft也是一样的,交易方式就有点像币圈的挂单吃单。

然后我们详细看一下mint的function,每一行我都配上了中文解析,可以发现并没有数量限制,但是有暂停功能,而且使用EIP1271,OpenZeppelin的SignatureChecker来检测签名,也就是如果我们能拿到官方的签名即可mint,无需去看视频。

    function mint(
        uint256 _category, ## 种类
        bytes memory _data, ## 签名中的V,实际逻辑中并无使用。
        bytes memory _signature ## 签名
    ) external nonReentrant whenNotPaused {
        require(isSignatureValid(_category, _signature), "LDRT: Invalid signature"); ## 验证签名
        require(_category >= 1, "LDRT: Invalid category. It is less than 1."); ## 验证输入的种类id要大于等于1
        require(_category <= 9, "LDRT: Invalid category. It is greater than 9."); ## 验证输入的种类id要小于等于9

        bytes32 hashAdrrCategory = keccak256(abi.encodePacked(msg.sender, _category)); 
        bool hasMinted = categoriesMinted[hashAdrrCategory]; 
        require(
            !hasMinted,
            "LDRT: Address already has token for that category."
        );  ##上面几行验证一个地址只能mint 1个同一个种类的
        categoriesMinted[hashAdrrCategory] = true; ##存放这个地址已经mint过这个种类
        // 1 is because it will mint 1 token for that category
        _mint(msg.sender, _category, 1, _data); ## mint nft
    }

如何拿到签名

先理解签名,相当于将你的地址和你要mint的nft的种类id打包成消息,然后将这个消息进行签名,签名需要官方的私钥签名,那我们肯定没有。这个时候就得去看正规途径是如何mint nft的,也就是看视频扫二维码怎么mint,一般经过抓包分析之后就可以伪造请求,我常用抓包软件charles。不过这次抓包是朋友直接发给我的。下次有空详细讲解一下抓包,无论是电脑手机还是其他硬件,很多Gamefi交互,刷交互等都用得上。直接贴获取签名的python代码。

def get_sign(address, category):
    headers = {
        'Authority': 'us-central1-ldr-prod.cloudfunctions.net',
        'Accept': 'application/json, text/plain, */*',
        'Accept-Language': 'zh-CN,zh;q=0.9',
        'Origin': 'https://lovedeathandart.com',
        'Referer': 'https://lovedeathandart.com/',
        'Sec-Fetch-Dest': 'empty',
        'Sec-Fetch-Mode': 'cors',
        'Sec-Fetch-Site': 'cross-site',
        'User-Agent': 'Mozilla/5.0 (iPhone; CPU iPhone OS 13_2_3 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/13.0.3 Mobile/15E148 Safari/604.1',
    }

    json_data = {
        'address': address,
        'category': category,
    }

    response = requests.post('https://us-central1-ldr-prod.cloudfunctions.net/api/sign', headers=headers,
                             json=json_data)
    print(response.json()["v"], response.json()["signature"])
    return response.json()["v"], response.json()["signature"]

其实这个签名就是简单的输入了address和category即可拿到签名,爱死机官方并没有做其他鉴权或者限制,也就是任何一个用户都可以调用接口直接拿到签名。

如果批量化脚本Mint

昨天看到已经有网页端链接小狐狸mint的开源代码,对于小白用户来说已经很好用了,但是作为“科学家”任何东西肯定要掌握在自己手上,多钱包肯定批量直接mint更方便。这个时候就需要学会如何直接在代码里面调用合约。python可以直接配合brownie框架(需要学习),简单举例一行代码即可调用合约LDR=Contract.from_explorer("合约地址"),当然也可以填入abi的方式进行合约调用。这个时候如果有多个钱包也就是读出每个钱包,然后分别mint就行了,无任何上限,除非官方关闭获取签名接口或者暂停合约mint。

def mint_nft():
    account = get_account()
    for i in range(1,10):
        data, sign = get_sign(str(account), str(i))
        LDR = Contract.from_explorer("0x2818Fae15D09744c0Ec5B98DbE539428058891B4")
        LDR.mint(str(i), data, sign, {"from": account})
        print("mint over")

小白用户怎么体验

如果既不想看合约又不想写代码,就想单纯的体验下怎么直接从合约mint nft,而不是从官方网站mint,那么可以看下文如何免Gas mint。建议用新钱包空钱包操作~

我已经将相同的合约部署在了polygon testnet,并且去除了签名限制。(合约开源安全)所以可以直接在polygon测试网玩一玩。

1.首先领水龙头,也就是测试代币,输入自己的地址确认即可。

https://faucet.polygon.technology/

2.将自己的小狐狸钱包切换到polygon测试网,不会的话去chainlist添加,如下图右下角。这个时候你会发现钱包里面有matic代币。没有的话就多等等或者去水龙头在领一次。

3.去浏览器上面调用合约链接如下

https://mumbai.polygonscan.com/address/0x2818Fae15D09744c0Ec5B98DbE539428058891B4#code

找到Contract,点击Write,点击Connect to web3,链接小狐狸

找到mint,第一个参数就是1-9里面的种类,因为去掉了签名,所以第二和第三参数按照格式随便填,然后点击write,就可以发送消息。

4.去opensea测试网检查是否有nft,如果出现拥有LDR的nft即成功,没有图片是因为这个nft并没有设置url,也就是没有设置图片。

https://testnets.opensea.io/account

总结: 绝大多数的nft,如果知道合约地址,即可使用类似思路进行抢mint,如果有编程基础,可以尝试直接在开mint前直接提前准备好调用合约,定时执行。有些合约是固定高度开放,有些会是发送消息来当开关,即可读取消息池来做到快速甚至同一个高度直接mint,因为不同合约实现思路和玩法会不同,需要自己针对项目进行代码修正。整体来说,如果快速上手js或者python,都可以做到更快的调用合约,抢土狗抢nft等都可以玩,有兴趣的可以学习一下。

ps:我心中认为的是科学家是深度钻研技术的人,也就是科研方向。我自身只是个简单的build,并称不上科学家~取这个标题就是让感兴趣的大家一起来build。

watch to earn貌似也是个不错的思路,但是如何做到安全性上的保证是需要思考的。