Solidity
函式沒有參數時如何生成簽名?
當函式有參數時,Solidity 通過在函式名稱後面添加參數類型,在括號之間,並獲取結果字元串的 keccak256 雜湊來生成其簽名。舉個例子:
sendMessage(string,address)
這個函式的簽名是 0xc48d6d5e。
但是,如果“字元串”和“地址”參數不存在怎麼辦?Solidity 會採用 , 或其他的 keccak256 雜湊
sendMessage
嗎sendMessage()
?
一個簡單的測試表明答案是
"sendMessage()"
。Solidity 合約:
pragma solidity 0.6.12; contract MyContract { uint256 private constant SUCCESS = 42; uint256 private constant FAILURE = 84; function sendMessage() external pure returns (uint256) { return SUCCESS; } function test(bytes4 funcSelector) external view returns (uint256) { bytes memory data = abi.encodeWithSelector(funcSelector); (bool success, bytes memory returnData) = address(this).staticcall(data); if (success && returnData.length == 32) return abi.decode(returnData, (uint256)); return FAILURE; } }
松露 5.x 腳本:
contract("MyContract", () => { it("test", async () => { const myContract = await artifacts.require("MyContract").new(); const success = await myContract.test(web3.utils.keccak256("sendMessage()")); const failure = await myContract.test(web3.utils.keccak256("sendMessage")); console.log(success.toString()); // prints 42 console.log(failure.toString()); // prints 84 }); });
這是一種更簡單的方法,甚至無需與合約互動:
const Web3 = require("web3"); const web3 = new Web3(); const abi = [{ "inputs":[], "name":"sendMessage", "outputs":[], "stateMutability":"pure", "type":"function" }]; const contract = new web3.eth.Contract(abi); console.log(Web3.utils.keccak256("sendMessage").slice(0, 10)); console.log(Web3.utils.keccak256("sendMessage()").slice(0, 10)); for (const method of contract._jsonInterface) if (method.name == "sendMessage") console.log(method.signature);
列印輸出是:
0x736c24a9 0xe5aed28a 0xe5aed28a