1 开发工具
使用eosio-cpp
工具来进行开发
1 | brew tap eosio/eosio.cdt |
2 创建合约目录 hello
1 | mkdir hello |
注意: 合约目录非常重要,因为 EOS 的合约部署是以目录来进行的。
3 创建一个合约文件 hello.cpp
1 | touch hello.cpp |
文件名无所谓,惯例是合约名 +
.cpp
4 Hello World 合约
1 | vim hello.cpp |
合约内容
1 | #include <eosiolib/eosio.hpp> |
5 合约详解
5.1 引入头文件
最重要的头文件是 <eosiolib/eosio.hpp>
,该头文件包含了大量的其它头文件。
1 | #pragma once |
源代码在 https://github.com/EOSIO/eosio.cdt/blob/master/libraries/eosiolib/eosio.hpp
5.2 宏定义
1 | #define CONTRACT class [[eosio::contract]] |
这三个宏定义分别用来修饰一个 **合约** 、**动作** 、**表**
5.3 命名空间
引入命名空间 eosio
。EOS 把所有的类和函数都放在 eosio
命名空间下。
1 | #include <eosiolib/eosio.hpp> |
5.4 继承
EOS 中所有的合约都必须继承自一个基础合约 eosio::contract
。 该基础合约在 <eosiolib/contract.hpp>
头文件中定义
1 | #include <eosiolib/eosio.hpp> |
5.5 动作 action
EOS 合约可以包含一些动作 ( action
) 和一些用于存储数据的表 table
,这些表都是一个结构体 struct
。 如果不用存储数据,那么表是可以忽略的。
EOS 合约中的动作都需要 [[eosio::action]]
属性来修饰。
1 | #include <eosiolib/eosio.hpp> |
5.6 输出
需要输出信息,比如一些字符串等,可以使用 eosio::print()
方法。
eosio::print()
方法在 <eosiolib/print.hpp>
头文件中定义
1 | #include <eosiolib/eosio.hpp> |
5.7 定义动作
一个 EOS 合约中可以有多个动作 action ,当 EOS 接收到一个事务后,会将该事务分发给相应的合约,或者说,调用相应的合约的动作。
为了确保合约的哪个动作可以调用,需要使用 EOSIO_DISPATCH
宏来告诉 EOS。
EOSIO_DISPATCH
宏在 <eosiolib/dispatcher.hpp>
头文件中定义,该宏的第一个参数是合约的名字,第二个参数,是多个小括号 ()
扩起来的多个动作的方法名。
1 | #include <eosiolib/eosio.hpp> |
6 编译合约
使用 eosio-cpp
命令来编译合约
1 | eosio-cpp -o hello.wasm hello.cpp --abigen |
6.1 选项说明
选项 | 说明 |
---|---|
-o hello.wasm | 该选项用于指定合约编译后的输出文件。必须是以 .wasm 作为文件扩展名 |
hello.cpp | 合约源文件 |
–abigen | 该选项用户指定合约编译时同时生成 abi 文件 |
运行该命令输出结果如下
1 | $ eosio-cpp -o hello.wasm hello.cpp --abigen |
编译完成后,当前 hello
目录就会多出两个文件
1 | $ ls |
7 部署合约
部署合约的前提就是需要存在一个账户。在前面的章节中,我们创建了一个 hello
账户,接下来我们就使用在这个账户上部署合约
部署合约需要使用到 cleos set contract
命令。
1 | cleos set contract hello ../hello -p hello@active |
7.1 选项说明
选项 | 说明 |
---|---|
cleos set contract | 部署合约的命令 |
hello | 部署合约的账户,必须已经存在 |
../hello | 合约所在的目录名,该目录下必须包含和目录相同的 .wasm 和 .abi 文件 |
-p hello@active | 该选项用于指定权限,该权限必须包含 hello 账户的 active 权限 |
该命令的运行结果如下
1 | Reading WASM from ../hello/hello.wasm... |
8 运行合约下的动作
只能说是 hello
账户下部署了一个合约,该合约下有一个动作 hi
。
如果我们要执行这个账户下的合约的 hi
动作,需要使用到 cleos push action
命令。该命令的语法如下
1 | cleos push action hello hi '[]' -p hello@active |
8.1 参数说明
选项 | 说明 |
---|---|
cleos push action | 执行合约动作的命令 |
hello | 合约所在的账户名 |
hi | 要执行的合约的动作,必须是已经导出的,也就是 EOSIO_DISPATCH( hello, (hi)) 中定义的 |
-p hello@active | 用于执行合约的权限,可以是任意权限,只要该合约运行 |
运行上面的命令,输出结果如下
1 | executed transaction: 843a65cd56420c6f749a10cf221fdf36716067cd1718c8348c38a304ba752ab0 96 bytes 270 us |
看到最后的那个 >> Hello World
吗? 这个就是 print("Hello World");
的输出结果