博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
实现一个可管理、增发、兑换、冻结等高级功能的代币
阅读量:7084 次
发布时间:2019-06-28

本文共 4592 字,大约阅读时间需要 15 分钟。

本文主要介绍代币高级功能的实现: 代币管理、代币增发、代币兑换、资产冻结、Gas自动补充。

写在前面

在中我们实现一个最基本功能的代币,本文将在上一遍文章的基础上,讲解如果添加更多的高级功能。

实现代币的管理者

虽然区块链是去中心化的,但是实现对代币(合约)的管理,也在许多应用中有需求,为了对代币进行管理,首先需要给合约添加一个管理者。

我们来看看如果实现,先创建一个owned合约。

contract owned {        address public owner;        function owned() {            owner = msg.sender;        }        modifier onlyOwner {            require(msg.sender == owner);            _;        }        // 实现所有权转移        function transferOwnership(address newOwner) onlyOwner {            owner = newOwner;        }    }复制代码

这个合约重要的是加入了一个函数修改器(Function Modifiers)onlyOwner,函数修改器是一个合约属性,可以被继承,还能被重写。它用于在函数执行前检查某种前置条件。 关于函数修改器可进一步阅读

如果熟悉Python的同学,会发现函数修改器的作用和Python的装饰器很相似。

然后让代币合约继承owned以拥有onlyOwner修改器,代码如下:

contract MyToken is owned {    function MyToken(        uint256 initialSupply,        string tokenName,        uint8 decimalUnits,        string tokenSymbol,        address centralMinter        ) {        if(centralMinter != 0 ) owner = centralMinter;    }}复制代码

代币增发

实现代币增发,代币增发就如同央行印钞票一样,想必很多人都需要这样的功能。

给合约添加以下的方法:

function mintToken(address target, uint256 mintedAmount) onlyOwner {        balanceOf[target] += mintedAmount;        totalSupply += mintedAmount;        Transfer(0, owner, mintedAmount);        Transfer(owner, target, mintedAmount);    }复制代码

注意onlyOwner修改器添加在函数末尾,这表示只有ower才能调用这用函数。 他的功能很简单,就是给指定的账户增加代币,同时增加总供应量。

资产冻结

有时为了监管的需要,需要实现冻结某些账户,冻结后,其资产仍在账户,但是不允许交易,之道解除冻结。 给合约添加以下的变量和方法(可以添加到合约的任何地方,但是建议把mapping加到和其他mapping一起,event也是如此):

mapping (address => bool) public frozenAccount;    event FrozenFunds(address target, bool frozen);    function freezeAccount(address target, bool freeze) onlyOwner {        frozenAccount[target] = freeze;        FrozenFunds(target, freeze);    }复制代码

单单以上的代码还无法冻结,需要把他加入到transfer函数中才能真正生效,因此修改transfer函数

function transfer(address _to, uint256 _value) {        require(!frozenAccount[msg.sender]);        ...}复制代码

这样在转账前,对发起交易的账号做一次检查,只有不是被冻结的账号才能转账。

代币买卖(兑换)

可以自己的货币中实现代币与其他数字货币(ether 或其他tokens)的兑换机制。有了这个功能,我们的合约就可以在一买一卖中赚利润了。

先来设置下买卖价格

uint256 public sellPrice;    uint256 public buyPrice;    function setPrices(uint256 newSellPrice, uint256 newBuyPrice) onlyOwner {        sellPrice = newSellPrice;        buyPrice = newBuyPrice;    }复制代码

setPrices()添加了onlyOwner修改器,注意买卖的价格单位是wei(最小的货币单位: 1 eth = 1000000000000000000 wei)

添加来添加买卖函数:

function buy() payable returns (uint amount){        amount = msg.value / buyPrice;                    // calculates the amount        require(balanceOf[this] >= amount);               // checks if it has enough to sell        balanceOf[msg.sender] += amount;                  // adds the amount to buyer's balance        balanceOf[this] -= amount;                        // subtracts amount from seller's balance        Transfer(this, msg.sender, amount);               // execute an event reflecting the change        return amount;                                    // ends function and returns    }    function sell(uint amount) returns (uint revenue){        require(balanceOf[msg.sender] >= amount);         // checks if the sender has enough to sell        balanceOf[this] += amount;                        // adds the amount to owner's balance        balanceOf[msg.sender] -= amount;                  // subtracts the amount from seller's balance        revenue = amount * sellPrice;        msg.sender.transfer(revenue);                     // sends ether to the seller: it's important to do this last to prevent recursion attacks        Transfer(msg.sender, this, amount);               // executes an event reflecting on the change        return revenue;                                   // ends function and returns    }复制代码

加入了买卖功能后,要求我们在创建合约时发送足够的以太币,以便合约有能力回购市面上的代币,否则合约将破产,用户没法先合约卖代币。

实现Gas的自动补充

以太坊中的交易时需要gas(支付给矿工的费用,费用以ether来支付)。而如果用户没有以太币,只有代币的情况(或者我们想向用户隐藏以太坊的细节),就需要自动补充gas的功能。这个功能将使我们代币更加好用。

自动补充的逻辑是这样了,在执行交易之前,我们判断用户的余额(用来支付矿工的费用),如果用户的余额非常少(低于某个阈值时)可能影响到交易进行,合约自动售出一部分代币来补充余额,以帮助用户顺利完成交易。

先来设定余额阈值:

uint minBalanceForAccounts;    function setMinBalance(uint minimumBalanceInFinney) onlyOwner {         minBalanceForAccounts = minimumBalanceInFinney * 1 finney;    }复制代码

finney 是货币单位 1 finney = 0.001eth 然后交易中加入对用户的余额的判断。

function transfer(address _to, uint256 _value) {        ...        if(msg.sender.balance < minBalanceForAccounts)            sell((minBalanceForAccounts - msg.sender.balance) / sellPrice);        if(_to.balance

代码部署

高级功能完整代码请前往我的, 项目的完整的部署方法参考,不同的是创建合约时需要预存余额,如图:

专栏已经有多篇文章介绍Remix Solidity IDE的使用,这里就不一一截图演示了,请大家自己测试验证。

如何创建代币发行代币,现在也录制了对应的**** 目前我们也在招募体验师,可以点击了解。

如果你在创建代币的过程中遇到问题,欢迎到我的****提问,作为星球成员福利,成员可加入区块链技术付费交流群。

参考文档

- 系统学习区块链,打造最好的区块链技术博客。

转载地址:http://qzmml.baihongyu.com/

你可能感兴趣的文章
报名 | 清华方圆系列之大数据分析与可视化报告会将于下周举办
查看>>
了解 php.ini
查看>>
异地容灾方案解析
查看>>
深入理解Vue的生命周期
查看>>
WPF's Style BasedOn
查看>>
.NET Core实战项目之CMS 第十章 设计篇-系统开发框架设计
查看>>
.NET服务安装、卸载、启动、停止、判断是否存在
查看>>
基于深度学习的推荐系统综述 (arxiv 1707.07435) 译文第一、二章
查看>>
自定义抖动表单
查看>>
vue的组件通信
查看>>
iOS开发之让列表滚回最顶端最佳实践
查看>>
让开发变得更简单 | 阿里云中间件推出全新开发者服务
查看>>
HTML与CSS布局技巧总结
查看>>
elk(日志监控系统搭建),elastic search,kibana,logstash,filebeat搭建
查看>>
现场剪光缆!ATEC上支付宝模拟自断一半服务器,26秒一切恢复正常
查看>>
世界上最流行的编程语言恰恰也是大多数黑客的首选武器
查看>>
hadoop,spark,Zookeeper,,, 这些名字都是怎么来的呢?
查看>>
(5)学习笔记 ) ASP.NET CORE微服务 Micro-Service ---- 熔断降级(Polly)
查看>>
“六面魔方”里的浪潮
查看>>
聚焦理论—《可以量化的管理学》
查看>>