Skip to content

Latest commit

 

History

History
214 lines (171 loc) · 4.78 KB

tutorial_cn.md

File metadata and controls

214 lines (171 loc) · 4.78 KB

快速入门

相关工具

  • cargo
  • rust
  • ontio-cdk

开始

  1. 生成ontio-cdk api文档

克隆https://github.com/ontio/ontology-wasm-cdt-rust.git项目到本地,然后进入项目根目录,执行cargo doc命令生成api文档。

  1. 合约中数据类型转换
  • u64转换成string 示例
let s = 123.to_string();
  • base58编码的地址转换成Address 示例
let address = ostd::base58!("AFmseVrdL9f9oyCzZefL9tG6UbvhPbdYzM");
  1. 合约中验证签名

示例

let flag = runtime::check_witness(&from);
  1. 合约与合约交互

在合约中调用其他合约时,需要按照目标合约的参数序列化标准序列化参数。

  • wasm合约调用neovm合约
    • U128数据类型的序列化,需要先调用types::to_neo_bytes()方法转换成字节数组,然后在调用``。
    • Address数据类型要用sink.write_neovm_address()方法序列化。
    • 参数序列化步骤
      1. 先序列化要调用合约中方法的参数,目标合约的方法参数要按照倒序的方式序列化
      2. 方法参数序列化完成后,再序列化83u8193u8字节码
      3. 序列化方法名
      4. 序列化字节码103u8
      5. 序列化合约地址
      let mut sink = Sink::new(16);
      sink.write(to_neo_bytes(amount));
      sink.write_neovm_address(to);
      sink.write_neovm_address(from);
      sink.write(83u8);
      sink.write(193u8);
      sink.write("transfer".to_string());
      sink.write(103u8);
      sink.write(contract_address);
      let res = runtime::call_contract(contract_address, sink.bytes());
      
  • wasm调用native
    • wasm调用ontong中的方法请参考contract模块

ontio-std介绍

  1. abi 模块
  • Sink : 用于合约中数据类型的序列化 对于实现Encoder接口的数据类型都可以直接用sink.write()方法进行序列化, sink进行初始化的时候,会初始化一个Vec,需要指定其初始化大小。

示例

let mut sink = Sink::new(16);
sink.write(83u8);
sink.write("transfer".to_string());
  • Source: 用于合约中数据类型的反序列化

对于实现Decoder接口类型的数据类型可以直接用source.read().unwrap()方法进行反序列化

示例

let input = runtime::input();
let mut source = Source::new(&input);
let (from, to, amount) = source.read().unwrap();
  1. console 模块
  • debug:用于在合约中打印调试信息

示例

 console::debug("debug");
  1. contract模块
  • ong:封装了在合约中调用ong的相关操作,例如转账、查询余额等。
    • allowance(from: &Address, to: &Address) 查询allowance余额 示例
    use ostd::contract::ont;
    ont::allowance(from, to)
    
    • approve(from: &Address, to: &Address, amount: U128) 一个地址允许另一个地址转移多少资产

      示例

    use ostd::contract::ont;
    ont::approve(from, to, amount)
    
    • balance_of 查询余额

      示例:

      use ostd::contract::ont;
      ong::balance_of(address)
      
    • transfer 转账

      示例

    let state = ont::State { from: from.clone(), to: to.clone(), amount: amount };
    ont::transfer(&[state])
    
    • transfer_from

      示例

    ont::transfer_from(sender, from, to, amount)
    
  • ont:封装了在合约中调用ont的相关操作,调用方法和ong类似。
  1. database 模块
  • delete: 根据key删除数据库中的数据
  • get : 根据key查询数据
  • put : 根据key存储数据

示例:

use ostd::database;
database::put(from, frmbal);
let balance = database::get(owner).unwrap_or(0);
  1. types 模块
  • Address: 地址,是长度为20的字节数组
  • U128 : 小端序的大整数。
  1. runtime 模块

该模块封装了合约和链交互的api

  • timestamp() -> u64 获得当前时间戳

示例

runtime::timestamp()
  • block_height() -> u32 获得当前区块高度

示例

runtime::block_height()
  • address() -> Address 获得当前合约地址

示例

runtime::address()
  • caller() -> Address 获得调用者的合约地址

示例

runtime::caller()
  • current_blockhash() -> H256 获得当前区块hash

示例

runtime::current_blockhash()
  • current_txhash() -> H256 获得当前交易hash

示例

runtime::current_txhash()
  • check_witness(addr: &Address) -> bool 校验签名

示例

runtime::check_witness(addr)
  • ret(data: &[u8]) -> ! 合约执行结束时调用,返回执行结果

示例

let mut dispatcher = ApiTestDispatcher::new(ApiTestInstance);
runtime::ret(&dispatcher.dispatch(&runtime::input()));
  • notify(data: &[u8]) 合约中推送事件

示例

runtime::notify("success".as_bytes());

合约例子

oep4

oep5

oep8