联盟链PlatONE支持WASM虚拟机。本文通过一系列代码示例讲解合约的各个功能,用户可以通过学习这些例子来深入理解如何编写一个应用合约。PlatONE代码获取
Contract类
Contract类是有bcwasm库提供的合约基类,用户开发的合约必须派生于该类。Contract类中定义了一个init()
虚函数,用户合约需要实现该init()
函数,该函数在合约首次发布时执行,仅调用一次,该方法作用类似于solidity合约中的构造函数。
注意: init()
方法必须实现为public
类型,这样合约在部署时才能够调用该函数来初始化合约数据。
#include <bcwasm/bcwasm.hpp>
namespace my_namespcase {
class my_contract : public bcwasm::Contract
{
public:
my_contract(){}
/// 实现父类: bcwasm::Contract 的虚函数
/// 该函数在合约首次发布时执行,仅调用一次
void init()
{
/* 做一些初始化操作 */
}
};
}
复制代码
合约外部方法
合约外部方法指的是合约可以在外部调用的接口,功能类似与solidity合约中的public
类型方法,在bcwasm库中是通过BCWASM_ABI
宏来定义外部方法。通过BCWASM_ABI
声明的方法,可以在合约外部通过rpc消息调用、也可以被其他合约调用。
#include <bcwasm/bcwasm.hpp>
namespace my_namespcase {
class my_contract : public bcwasm::Contract
{
public:
my_contract(){}
/// 实现父类: bcwasm::Contract 的虚函数
/// 该函数在合约首次发布时执行,仅调用一次
void init()
{
/* 做一些初始化操作 */
}
void setData(char * data){
/* 修改合约数据 */
}
};
}
// 外部方法
BCWASM_ABI(my_namespcase::my_contract:setData)
复制代码
链上存储接口
Wasm合约内置库为数据的持久化提供了setState()
方法,可以通过调用bcwasm::setState()
函数实现数据持久化,相应地查询调用bcwasm::getState()
。
下方的示例合约中,有两个接口供外部调用setData(char* data)
和getData()
。这两个方法分别调用了bcwasm::setState()
、bcwasm::getState()
,以实现数据的上链持久化和查询。
#include <bcwasm/bcwasm.hpp>
namespace my_namespcase {
class my_contract : public bcwasm::Contract
{
public:
void init(){}
void setData(char * data){
std::string m_data(data);
bcwasm::setState("DataKey", m_data);
}
const char* getData() const{
std::string m_data;
bcwasm::getState("DataKey", m_data);
return m_data.c_str();
}
};
}
// 外部方法
BCWASM_ABI(my_namespcase::my_contract, setData)
BCWASM_ABI(my_namespcase::my_contract, getData)
复制代码
Const方法
合约中的const
类型方法提供对合约状态的只读操作,该类型声明的函数不能够修改合约数据,一般用来查询合约的链上数据。下方代码中,getData()
即为const方法,用于查询数据。
const char* getData() const{
std::string m_data;
bcwasm::getState("DataKey", m_data);
// 读取合约数据并返回
return m_data.c_str();
}
复制代码
Struct、Map
Struct 结构体
结构体语法规则与C++一致,但是如果用于需要将结构数据上链持久化,则需要在结构体