Solidity modifier
Solidity 中关键字 modifier 用于声明一个函数修改器。函数修改器的作用与 Spring 中的切面功能很相似,当它作用于一个函数上,可以在函数执行前或后预先执行 modifier 中的逻辑,以增强其功能。
我们来看一个函数修改器经典的应用 OpenZeppelin 库中的 Ownable 合约,下面是其中关键的代码:
/// Ownable 可以判断合约的调用者是否为当前合约的owner, /// 从而避免其他人随意的调用一些合约的关键操作。 /// 同时,owner 可以指定任何其他人为此合约新的 owner, /// 显然,只有当前owner才能指定其他人为新的owner。 contract Ownable { // 变量 owner 指定此合约的owner address public owner; // 发布事件 - 此合约owner已经换人(此逻辑与modifier无关,可以忽略) event OwnershipTransferred(address indexed previousOwner, address indexed newOwner); // 构造函数 - 创建合约自动执行,初始化合约所有人为合约创建者 function Ownable() public { owner = msg.sender; } // 定义一个函数修改器 modifier onlyOwner() { // 判断此函数调用者是否为owner require(msg.sender == owner); _; } // owner可以用此函数将owner所有权转换给其他人,显然次函数只有owner才能调用 // 函数末尾加上onlyOwner声明,onlyOwner正是上面定义的modifier function transferOwnership(address newOwner) public onlyOwner { require(newOwner != address(0)); OwnershipTransferred(owner, newOwner); owner = newOwner; } }
上述合约的 transferOwnership 函数用于 owner 将所有权转让给其他人,于是在末尾声明 onlyOwner 修改器,onlyOwner 将在 transferOwnership 执行前,先执行
require(msg.sender == owner);
以保证此函数的调用者为 owner ,如果不是 owner 则抛出异常。
_ 的作用
函数修改器中有一行代码只有下划线 _ ,在实际执行中,我们可以将被修饰函数的代码视为下划线处的代码。即,下划线实际上帮我们标记了被 modifier 修饰函数的执行位置。如上例中
modifier onlyOwner() { require(msg.sender == owner); _; }
下划线在 require(msg.sender == owner) 后面,则被修饰函数 transferOwnership 在此判断条件之后执行。
Solidity modifier 功能与Spring中的切面非常相似,可以将一些通用的操作提取出来,提高编码效率,降低代码耦合性。智能合约支持继承,通过继承上述合约,可以直接使用其中定义的 OnlyOwner,在自己的合约中直接使用。
Solidity 众筹智能合约,提供一个安全、完整的 Solidity 智能合约案例,用于通过众筹方式进行筹资。 1. 募资人 struct Donee用于表示一个募资项目,其中包括募资人地址、目标 ...