ERC1155

Posted 长琴子

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了ERC1155相关的知识,希望对你有一定的参考价值。

ERC1155

ERC1155是一个为了实现比以前标准更好的新通证标准。

多通证标准

ERC1155最独特的功能是它使用一个单独的智能合约一次性代表多种通证。这也就是它的balanceOf函数与ERC20及ERC777不同的原因。它有一个额外的id参数作为通证标识符以查询余额。

这点和ERC721相似,但是表中的id并没有余额的概念。ERC721的balanceOf函数关联到一个账户拥有多少不同的通证,而不是每个拥有多少个。另一方面,ERC1155账户每个通证id有非常清晰的余额。和不可替代的通证实现通过简单铸造它们中的一个。

这种方法对于有多种通证的项目会节省大量的gas费。比针对每种通证类型部署不同的合约更好。一个ERC1155通证合约可以包含所有系统状态,降低部署成本和复杂性。

批量操作

因为所有状态都存储在一个合约中,就可以非常高效地在一个操作中操作很多通证。标准提供了两个函数:balanceOfBatch 和 safeBatchTransferFrom,使得查询多个余额和转移多种通证变得简单和花费更少的gas费。

在标准中,也包含一些非必需的函数,比如_mintBatch。

构造一个ERC1155通证合约

// contracts/GameItems.sol

// SPDX-License-Identifier: MIT

pragma solidity ^0.8.4;

import "@openzeppelin/contracts/token/ERC1155/ERC1155.sol";

contract GameItems is ERC1155

    uint256 public constant GOLD = 0;

    uint256 public constant SILVER = 1;

    uint256 public constant THORS_HAMMER = 2;

    uint256 public constant SWORD = 3;

    uint256 public constant SHIELD = 4;

    constructor() ERC1155("https://game.example/api/item/id.json")

        _mint(msg.sender, GOLD, 10**18, "");

        _mint(msg.sender, SILVER, 10**27, "");

        _mint(msg.sender, THORS_HAMMER, 1, "");

        _mint(msg.sender, SWORD, 10**9, "");

        _mint(msg.sender, SHIELD, 10**9, "");

    

ERC1155合约包含可选的扩展IERC1155MetadataURI。用于查询合约的元数据。

不像ERC20那样,ERC1155没有小数字段,每个代币就不可以再分割。

以上合约部署好以后,就可以查询部署者的余额

> gameItems.balanceOf(deployerAddress,3)

也可以转移

> gameItems.safeTransferFrom(deployerAddress, playerAddress, 2, 1, "0x0")

> gameItems.balanceOf(playerAddress, 2)

1

> gameItems.balanceOf(deployerAddress, 2)

0

也可以批量转移和批量获取余额

> gameItems.safeBatchTransferFrom(deployerAddress, playerAddress, [0,1,3,4], [50,100,1,1], "0x0")

> gameItems.balanceOfBatch([playerAddress,playerAddress,playerAddress,playerAddress,playerAddress], [0,1,2,3,4])

[50,100,1,1,1]

元数据uri获取方式:

> gameItems.uri(2)

"https://game.example/api/item/id.json"

Uri可以包含字符串id,客户端查询时替换为实际的代币id,小写的十六进制格式,不够64位的用0填充。对于代币ID为2的可以这样查询:

https://game.example/api/item/0000000000000000000000000000000000000000000000000000000000000002.json

查询的元数据如下所示:

    "name": "Thor's hammer",

    "description": "Mjölnir, the legendary hammer of the Norse god of thunder.",

    "image": "https://game.example/item-id-8u5h2m.png",

    "strength": 20

给合约发送代币

当使用safeTransferFrom做代币转移时的一个重要区别是可能收到以下消息

ERC1155: transfer to non ERC1155Receiver implementer

这就对了,这意味着接受合约还没有注册自己为ERC1155协议。

为了接收ERC1155代币我们可以继承合约ERC1155Holder。

// contracts/MyContract.sol

// SPDX-License-Identifier: MIT

pragma solidity ^0.8.4;

import "@openzeppelin/contracts/token/ERC1155/utils/ERC1155Holder.sol";

contract MyContract is ERC1155Holder

也可以通过onERC1155Received和onERC1155BatchReceived 函数实现更多复杂的场景应用。

预置ERC1155合约

ERC1155PresetMinterPauser,这个预置合约包含铸造和批量铸造功能,以及转移和销毁功能。合约通过使用 Access Control 控制对铸造和中止函数的访问。已部署合约的账号会授权给铸造者或者中止者角色,还有默认的管理员角色。

这个合约可以在没有任何Solidity代码的情况下用于部署,用于快速作原型或测试,当然也可以直接使用与生产环境。

ERC20、ERC223、ERC721和ERC948的区别?

【中文标题】ERC20、ERC223、ERC721和ERC948的区别?【英文标题】:Difference between ERC20, ERC223, ERC721 and ERC948? 【发布时间】:2019-03-28 13:06:46 【问题描述】:

我是 Solidity 的新手。我得到了很多类型的稳固性,但我无法了解所有类型的 ERC 的实际差异。谁能给我解释一下异同。

【问题讨论】:

【参考方案1】:

ERC20 是当今大多数人都知道和喜爱的令牌标准。该标准定义了基本的令牌需求,例如_totalSupplytransfer()approve()transferFrom()。您必须定义令牌的namesymboldecimals。它还定义了一个balances 映射,用于跟踪每个用户的资产等。

ERC223 是 ERC20 的扩展,可防止代币意外转移到代币合约本身(而不是其他用户)。当发起 ERC20 转账时,实际上发生的是与代币合约的交互,这会触发余额的变化。正因为如此,人们会感到困惑并不小心将代币发送到代币合约,从而有效地永久销毁它们。其实现很简单:扩展 ERC20 接口并添加一个带有附加参数的附加 transfer() 函数(以避免覆盖 ERC20 transfer())。如果使用这个transfer()函数,如果代币被发送到代币合约,交易将会失败。

ERC721 与上述 EIP 的不同之处在于它是一种新型令牌。这是一个不可替代的代币,这意味着每个代币都有一个唯一的 ID。这允许人们对独特的资产进行标记,例如房地产或加密猫。通过允许创建独特的、单独的代币,用户现在可以像跟踪现实世界中的传统资产一样跟踪这些代币。

ERC948 是在以太坊上基于订阅支付的提议。这个想法是许多人通过基于订阅的服务获得报酬,这个 ERC 提出了一种使用以太币或代币在以太坊中实现这一点的方法。

【讨论】:

以上是关于ERC1155的主要内容,如果未能解决你的问题,请参考以下文章

ERC1155

代币标准--ERC1155协议源码解析

以太坊 ERC-20 ERC-721 ERC-1155区别对比

,让你了解ERC-1155 多代币标准协议

初探区块链数字加密资产标准ERC721

ERC1155实践欧阳询书法复制品从确权设计到买卖测试