1:永存留言
来一个好玩的项目来运行他,来学习他,这是比较有趣的方式。
一个非常简单的DAPP,永存留言。
里面的合约非常简单,复制到remix中编译运行即可。
编译错误将版本修改为:^0.4.26
我们简单解读一下:
1 | // 留言结构体 |
首先,他申明了一个建构体,你可以理解为对象。
该对象有三个属性,留言的内容String,留言的钱包地址address,留言的时间unix。
1 | Message[] private wordArr; |
然后申明了一个对象数组,用他来存储留言信息。
如果是Java程序,那么该类停止运行就结束了,但是以太坊EVM并不会停止,所以可以一直运行。
所以,把数据存储在链上,而不是MYSQL之类的数据库,这一点很重要。
2:改造方法
我们来看看他的两个方法,一个写入(付出GAS),一个读取(无需GAS):
1 | function setWord(string s, string t) public { |
push是sol中数组的方法,表示在尾部添加元素。
该方法传入两个参数,分别表示:留言和时间。
这种赋值的方法在JavaScript中叫解构(ES6语法),此处异曲同工,各种语言相互借鉴。
但是,如果时间信息由用户来传递是否会造成一些问题呢?
所以,我自己将参数t去掉,赋值操作为:timestamp: now
now获取当前时间(查百度的)。
这样就只需要输入留言内容即可。
读取的方法如下:
1 | function getRandomWord(uint random) public view returns (uint, string, address, uint256) { |
参数是random,如果对象数组没有留言就返回空,否则就返回数组中的random+1条留言。
这里有一个问题,如对象数组只有2条留言,我输入的random为10,他不会返回任何对象,这违背了程序设计的初衷。
所以,我们魔改一下:
1 | function getRandomWord(uint random) public view returns (uint, string, address, uint256) { |
我们加上温馨的提示,最后把提示人改成:0x0000000000000000000000000000000000000000,完美。
3:新功能
我觉得只有一个读取方法未免不合理,所以我决定加几个。
比如,读取最新消息:
1 | function getNewMessage() public view returns (uint, string, address, uint256) { |
但是,只有这个也太无聊了,我们还写一个叫,读取指定用户所有留言信息:
1 | function getAddressAllMessage(address add) public view returns (Message[] memory) { |
remix自带的ASK GPT帮助了我,因为我返回的时候一直报错。最后在顶部添加了一行:
1 | pragma experimental ABIEncoderV2; |
才算没有红色错误,只有黄色的警告,只要编译不出问题那就没有问题。
既然都有读取指定用户的所有留言,干脆出一个读取全部留言功能:
1 | /** |
我们就来部署一下。使用测试网来运行他:
https://sepolia.etherscan.io/address/0xc2755fdfa1ac3c8a98c3335003e179e40d29888f#readContract
可以拿来偶尔写点东西,唉嘿。
旁边的Read Contract可以用来查询。