-
Notifications
You must be signed in to change notification settings - Fork 256
Chain33 EVM 食品溯源案例
[TOC]
下面以基于Solidity语言的食品溯源智能合约,阐述如何在chain33平行链上设计,实现,部署和调用智能合约
具体过程参见 平行链环境搭建, 如果环境已经具备,则跳过这一步
创建钱包并导入创世地址私钥(已经创建钱包的话就无需进行这一步了):
# 生成随机数种子,建议可以手工生成并保存好,后继可以使用此种子恢复钱包,--rpc_laddr参数可以设定指向具体链的rpc地址(以下地址只是举例,需要根据自己实际监听的jrpc地址修改==>对应配置文件中的:jrpcBindAddr配置项)
$ ./chain33-cli --rpc_laddr="http://localhost:8901" seed generate -l 0
# 保存种子,并设置钱包密码为"fzm12345",注意:密码可以自定义(8位以上,字母+数字),并且牢牢记住,后面解锁钱包时会用到
$ ./chain33-cli --rpc_laddr="http://localhost:8901" seed save -p fzm12345 -s "上一步中生成的seed"
# 使用我们刚刚设置的密码解锁钱包(钱包新创建后默认为锁定状态),-t后跟的是自动锁定的时间,0代表永不锁定(重启例外)
$ ./chain33-cli --rpc_laddr="http://localhost:8901" wallet unlock -p fzm12345 -t 0
# 检查钱包的状态
$ ./chain33-cli --rpc_laddr="http://localhost:8901" wallet status
# 创建一个账户地址和私钥
$ ./chain33-cli --rpc_laddr="http://localhost:8901" account create -l testEvm
# 查询上述被创建账户的地址和私钥
$ ./chain33-cli --rpc_laddr="http://localhost:8901" account dump_key -a "上一步生成的地址"
# 查看账户
$ ./chain33-cli --rpc_laddr="http://localhost:8901" account list
注意:平行链节点执行指令时,需要添加
--rpc_laddr
,rpc_laddr表示平行链节点启动的IP和监听端口,如果不指定这个参数,默认是指向http://localhost:8801 (如果主链节点和平行链节点在同一台机器上,且主链端口是8801,那么不指定--rpc_laddr,命令就可能会跑错链)
查看平行链上区块同步的状态:
$ ./chain33-cli --rpc_laddr="http://localhost:8901" block last_header
{
"version": 0,
"parentHash": "0x905d3c3ab62718381436720382e436a52976b6798896c77c97cb4e751e3a67c9",
"txHash": "0x765a8babc9b63f7a5c608afb0943001741f3591f676026cd67dd99f6b3ad5122",
"stateHash": "0xeb240fe1248028e9c7271ae2838ea3970bb880031764c8154c8bce2d16262cb7",
"height": 57,
"blockTime": 1546501778,
"txCount": 1,
"hash": "0xac2be112305b231b9851a34f6db7bde1745a2b7c9c3a684c736dc59baf3e6e51",
"difficulty": 0
}
针对食品溯源这一场景,设计一个合约,实现产地,生产,流通等环节溯源, 合约满足以下特性: 实际溯源的环节是一个非常复杂的过程,这边精简为以下几个环节: 农牧场,食品厂,超市,食品质检部门,用户产品具备的属性,以生猪为例各环节操作:
-
支持添加生猪信息,修改生猪信息。
-
支持添加质检信息
-
支持添加超时上架信息
-
支持添加用户评分信息
-
支持上述信息的查询
合约代码参见:智能合约代码下载
下载解压并编译上述智能合约,参见ChainIDE配置与使用 拿到合约的bytecode和abi: bytecode: 60806040526000805560006001556000....省略后面部分,从IDE上拷贝... abi: [{"inputs":[{"internalType":"address","name":"_creator","type":"address"}....省略后面部分,从IDE上拷贝.....
部署和调用合约的命令行参数参见EVM合约部署
# 构造合约部署交易, --user.p.mbaas. 是平行链的title,此参数一定要填对,不然平行链上无法收到交易
./chain33-cli --rpc_laddr="http://localhost:8901" --paraName="user.p.mbaas." evm create -s foodTest -f 1000000 -c 上述btyecode值
# 签名交易 -k:合约部署人的私钥(此私钥匙对应的地址是: 1LQJbjsNxh6ve6RCXBuDnUuMQsqXsc4cWK, 此地址在下面计算合约地址时会用到)
./chain33-cli --rpc_laddr="http://localhost:8901" wallet sign -k 0xdb9415dfbd54ed84dccde80a0f9f2497c7b967116da92d8682900b324ea33d68 -d 上一步返回的数据
# 发送交易(返回的hash要记住,下面计算合约地址的时候会用到)
./chain33-cli --rpc_laddr="http://localhost:8901" wallet send -d 上一步签过名的数据
# 查询交易(在结果中 "receipt": {"ty": 2,"tyName": "ExecOk".....} 代表交易执行成功,如果ty=1,代表交易只是被打包但执行失败)
./chain33-cli --rpc_laddr="http://localhost:8901" tx query_hash -s 上一步返回的hash
# 如果上述交易执行返回ExecOk,代表合约部署成功,计算此合约的地址, --user.p.mbaas. 是平行链的title,此参数一定要填对 -a 合约部署人的地址 -s 上一步返回的hash(去掉前面0x的值),假设此处返回的是:174dwVy4fEY7WQkpuRZRci88BE5iuHHSY4
./chain33-cli --rpc_laddr="http://localhost:8901" --paraName="user.p.mbaas." evm calc -a 1LQJbjsNxh6ve6RCXBuDnUuMQsqXsc4cWK -s 上一步返回的hash去掉最前面的0x
农牧场出栏
出栏批次 | 名称 | 重量 | 出栏日期 | 产地 |
---|---|---|---|---|
00001 | pig001 | 500 | 20190221 | NanJing |
# 使用addPigInfo进行猪肉信息的录入
# 重要: 先在本地生成一个174dwVy4fEY7WQkpuRZRci88BE5iuHHSY4.abi文件,复制IDE中生成的abi内容到此文件中
# 其中174dwVy4fEY7WQkpuRZRci88BE5iuHHSY4替换成自己的合约地址
$ ./chain33-cli --rpc_laddr="http://localhost:8901" --paraName="user.p.mbaas." evm call -e 174dwVy4fEY7WQkpuRZRci88BE5iuHHSY4 -p "addPigInfo("1CbEVT9RnM5oZhWMj4fxUrJX94VtRotzvs","pig001","00001","500","20190210","NanJing")"
# -k是调用合约人的私钥
$ ./chain33-cli --rpc_laddr="http://localhost:8901" wallet sign -k 0xdb9415dfbd54ed84dccde80a0f9f2497c7b967116da92d8682900b324ea33d68 -d 上一步返回的结果
$ ./chain33-cli --rpc_laddr="http://localhost:8901" wallet send -d 上一步返回的结果
# 通过hash查看猪肉信息是否成功添加,如果返回"receipt": {"ty": 2,"tyName": "ExecOk".....} 代表交易执行成功,如果ty=1,代表交易只是被打包但执行失败)
$ ./chain33-cli --rpc_laddr="http://localhost:8901" tx query -s "上一步返回的hash"
# 使用getPigNumber()函数查看录入了多少条生猪信息
# 其中-a 174dwVy4fEY7WQkpuRZRci88BE5iuHHSY4替换成合约地址,-c为调用人地址,-b为合约中查询方法
$ ./chain33-cli --rpc_laddr="http://localhost:8801" --paraName="user.p.mbaas." evm query -a 174dwVy4fEY7WQkpuRZRci88BE5iuHHSY4 -c 1LQJbjsNxh6ve6RCXBuDnUuMQsqXsc4cWK -b "getPigNumber()"
# 通过getPigInfoByIndex函数,查询index对应的生猪详细信息
$ ./chain33-cli --rpc_laddr="http://localhost:8801" --paraName="user.p.mbaas." evm query -a 174dwVy4fEY7WQkpuRZRci88BE5iuHHSY4 -c 1LQJbjsNxh6ve6RCXBuDnUuMQsqXsc4cWK -b "getPigInfoByIndex(0)"
食品厂生产(比如火腿)
食品编号(比如二维码) | 名称 | 重量 | 生产日期 | 包装日期 | 保质期 | 猪肉出栏批次 |
---|---|---|---|---|---|---|
001 | food001 | 500 | 20190215 | 20190220 | 20210215 | 00001 |
上链和查询脚本和3.2.1中类似(具体方法名称和参数,请见Food.sol中定义)
食品质检部门抽检
食品编号(比如二维码) | 检测时间 | 检测结果 | 检测说明 |
---|---|---|---|
food001 | 20190226 | Qualified | The food is good. |
上链和查询脚本和3.2.1中类似(具体方法名称和参数,请见Food.sol中定义)
食品编号(比如二维码) | 上架日期 |
---|---|
food001 | 20190304 |
上链和查询脚本和3.2.1中类似(具体方法名称和参数,请见Food.sol中定义)
食品编号 | 用户评分 |
---|---|
food001 | 90 |
上链和查询脚本和3.2.1中类似(具体方法名称和参数,请见Food.sol中定义)
hello world