目录

安装 Go

安装第三方包管理工具glide

源码编译部署ONT本体测试链

Docker部署ONT本体测试链

创建ONT钱包

节点部署

本地测试网络部署节点

自动化交互后台运行

官方Polaris测试网部署节点


安装 Go

Golang官方下载,选中对应版本,复制地址。

wget https://dl.google.com/go/go1.10.1.linux-amd64.tar.gz

tar -zxvf go1.10.1.linux-amd64.tar.gz

cd go

# 获得go安装地址 /mnt/ont-dev/ontology/go

pwd

mkdir -p /mnt/ont-dev/GoPath

vim /etc/profile

# Shift + G跳至末尾行,添加环境变量

# 将GOROOT的值改成go安装地址

export GOROOT=/mnt/ont-dev/go

export GOPATH=/mnt/ont-dev/GoPath

export PATH=$PATH:$GOROOT/bin:$GOPATH/bin

# 最后生效以下环境变量

source /etc/profile .

# OK,查看一下go版本,验证是否安装成功

go version

安装第三方包管理工具glide

yum intall glide

yum intall git

源码编译部署ONT本体测试链

将源码拉取到$GOPATH/src/github.com/ontio/ontology目录

mkdir -p $GOPATH/src/github.com/ontio

git clone https://github.com/ontio/ontology.git

cd $GOPATH/src/github.com/ontio/ontology

拉取依赖包,此操作会消耗很长时间,但多数依赖都是从GitHub上拉取,并且有一部分依赖已失效(有些需要翻墙),需要手动从GitHub上一个个的下载,然后存放在指定位置。接下来我们拉取依赖:

glide install

通过make编译源码:

make all

!!!make all 会有报错,缺少依赖!!!

这时候可能会有小伙伴奇怪,为什么呢?原因是因为长城防火墙,导致了在glide install拉取依赖时网络不通畅,拉取失败了,在这里提供两种解决方案:


一、将上面红色标记处的依赖代码下载下来(完整的项目),让在指定位置,例如:缺少<github.com/ethereum/go-ethereum/common/fdlimit >,则访问https://github.com/ethereum/go-ethereum/common/fdlimit 发现是404,怎么办呢?

不用着急,我们找到go-ethereum工程,将源码下载下来。然后上传至服务器,并解压缩到GoPath对应的ethereum目录下面(目录不存在则手动创建),我们再次make all将不会再提示找不到fdlimit依赖。 

缺少的其它依赖按照上述方法操作即可!为防止小伙伴走丢,附上两张图:


二、作者提供当前版本(ontology v1.8.1)完整依赖压缩包GoPath.zip,将GoPath目录覆盖即可。将gopath.zip文件上传至/mnt/ont-dev:

unzip gopath.zip

继续尝试编译源码,make all:

如果出现如下错误信息,说明未将源码放在$GoPath/src/github.com/ontio目录下.

# command-line-arguments
./main.go:67:13: cannot use startOntology (type func(*"github.com/urfave/cli".Context)) as type "github.com/urfave/cli".ActionFunc in assignment
./main.go:71:6: cannot use cmd.AccountCommand (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:72:6: cannot use cmd.InfoCommand (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:73:6: cannot use cmd.AssetCommand (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:74:6: cannot use cmd.ContractCommand (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:75:6: cannot use cmd.ImportCommand (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:76:6: cannot use cmd.ExportCommand (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:77:6: cannot use cmd.TxCommond (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:78:6: cannot use cmd.SigTxCommand (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:79:6: cannot use cmd.MultiSigAddrCommand (type "github.com/ontio/ontology/vendor/github.com/urfave/cli".Command) as type "github.com/urfave/cli".Command in array or slice literal
./main.go:79:6: too many errors
make: *** [ontology] Error 2


编译完成会在源码根目录下生产两个文件:

ontology: 节点程序/以命令行方式提供的节点控制程序

tools/sigsvr: (可选)签名服务 - sigsvr是一个签名服务的server以满足一些特殊的需求。详细的文档可以在这里参考

可以看到这两个文件说明已经完成测试链的部署!

 

Docker部署ONT本体测试链

与源码编译一致,源码必须能通过make编译否则将无法打镜像,所以在打镜像前需要先make一下。将源码拉取到$GOPATH/src/github.com/ontio/ontology目录:

mkdir -p $GOPATH/src/github.com/ontio

git clone https://github.com/ontio/ontology.git

cd $GOPATH/src/github.com/ontio/ontology

 拉取依赖包,此操作会消耗很长时间,但多数依赖都是从GitHub上拉取,并且有一部分依赖已失效,需要手动从GitHub上一个个的下载,然后存放在指定位置。

glide install

make all

 如出现异常,请参考源码编译解决方案!编译完成会在源码根目录下生产两个文件:

make docker

可以看到,镜像已经生成,接下来我们让它跑起来:

docker run -ti ontio/ontology --networkid 2

-d后台运行,这里我们采用更直观的交互式运行,方便查看测试链区块同步状况,当然你也可以使用自动化交互后台启动。

可以开到启动后自动开始同步测试链区块。

重开一个客户端,查看正在运行的容器列表

docker ps

 接下来咱们需要进入镜像内部,以及找到节点控制程序:

docker exec -it adoring_chatelet bash

到这里Docker安装部分已经全部结束!接下来我们我们需要创建测试链钱包,接入测试网络。

创建ONT钱包

如果是编译部署,我们创建一个目录方便管理。

Cd /mnt/ont-dev/GoPath/src/github.com/ontio/ontology

#创建一个目录用来存放,节点客户端程序以及钱包文件

mkdir /mnt/ont-dev/ont

# copy一份节点客户端程序

cp ontology /mnt/ont-dev/ont

Cd /mnt/ont-dev/ont

接下来我们开始创建钱包,按照默认设置创建一个钱包账户,默认配置如下:

签名算法

ecdsa

曲线

P-256

签名方案

SHA256withECDSA

./ontology account add --default

 输入设置钱包文件密码123456,密码丢失,钱包文件将无法解密,也就意味着你的私钥丢失了:

Address:AWFjLjTSmsKUTZJp7YxKpq5pXagyoJjSsn

Public key:02af0752af9d669a29cdddc6c625b8e66b0c81eacf37d7d47653bdd3dc7eaac786

Signature scheme:SHA256withECDSA

Create account successfully.

先不要急着查看地址余额,启动测试网络之后才能查看。

节点部署

本地测试网络部署节点

首先需要创建一个默认钱包(如果你已经创建了默认钱包请忽略此步):

./ontology account add --default

 如下为我生成的账户钱包地址:

Address:AMMWWMW77HTB1VyW6jdGu3utWxd78DZetA

Public key:0222415b7caf12cbe2efe19eaa4a7861e1b8c24decaae4e0a72764eaf267f67f83

Signature scheme:SHA256withECDSA

Create account successfully.

$ ./ontology --testmode --enable-consensus

#--testmode 本地测试网部署
#--enable-consensus 开启节点共识,不开启将不会产生区块,所以必须开启,这点很重要!!
#--disable-rpc 关闭rpc服务
#--disable-event-log是关闭日志服务
#--config 设置创世区块配置文件
#--account 设置钱包账户
#--gasprice 燃油价格
#--gaslimit 所能支付的最大燃油费,如果单笔交易超过了这个值,将会中断交易,而已经使用的Gas将不会退还。
#注:通过--help可以查看所有命令的帮助信息哦~

查看一下地址余额:

注:如果你看到的余额为0,请在启动本地测试网络之后再进行查看。

自动化交互后台运行

1、安装expec

yum install tcl-devel
yum install expect

#注:expect是一个自动化交互套件,主要应用于执行命令和程序时,系统以交互形式要求输入指定字符串,实现交互通信。

2、创建start.sh文件

cd /mnt/ont-dev/ont
vim start.sh

输入以下内容:

#!/usr/bin/expect -f  
# 上一句,指定通过expect来运行此脚本

# 通过spawn 启动
spawn ./ontology --testmode --enable-consensus 
# 指定当出现"Password:"关键字的时候帮助我们完成交互
expect "Password:"  
# send当出现关键字的时候输入一下内容 “\n”==回车
send -- "123456\n"  
# interact保持交互状态,没有interact将会直接退出
interact

3、启动节点,指定控制台日志输出到ont.log文件

./start.sh  > ont.log 2>&1 &

4、查看一下端口,检查是否启动成功,可以看到如下三个端口表示启动成功:

netstat -ntpl

查看一下控制台日志:

我们发现,ong.log只保存了部分日志,这是因为存在两层交互的原因,ont.log只能收录到start.sh文件的输出,而start.sh中与expect交互部分的输出是无法收录的,简单的说就是已经夸应用了,如果想要查看详细的日志,可以去ONT日志Log文件夹中查看:

cd /mnt/ont-dev/ont/Log

查看最近日期的日志文件:

tail -200f 2019-11-27_10.40.32_LOG.log

官方Polaris测试网部署节点

./ontology --networkid 2

详细参数同上。由于测试网络节点太多,同步时间太长,开发不推荐部署使用,区块高度比主网高出48w左右。

Polaris 测试区块浏览器

测试网络部署后创建的账户余额为0,所以需要在官方申请测试币

主网节点部署

官方推荐记账节点配置:

./ontology --enable-consensus --disable-rpc --disable-event-log

主网区块浏览器地址

Java 钱包开发实战篇

ONT为实际数量为整数,ONG为实际数量×10^9精度为9每笔交易收取0.01ONG。

ONT 和 ONG 的地址为大小写敏感,请务必注意

对于在主网转账,请将 gaslimit 设为 20000,gasprice 设为500

创建ONT钱包

如果是编译部署,我们创建一个目录方便管理。

Cd /mnt/ont-dev/GoPath/src/github.com/ontio/ontology

 

//创建一个目录用来存放,节点客户端程序以及钱包文件

mkdir /mnt/ont-dev/ont

 

// copy一份节点客户端程序

cp ontology /mnt/ont-dev/ont

 

Cd /mnt/ont-dev/ont

接下来我们开始创建钱包:

 

// 按照默认设置创建一个钱包账户,默认配置如下:

//签名算法:ecdsa

//曲线:P-256

//签名方案:SHA256withECDSA

 

./ontology account add --default

 

// 输入设置钱包文件密码123456,密码丢失,钱包文件将无法解密,也就意味着你的私钥丢失了

 

Address:AWFjLjTSmsKUTZJp7YxKpq5pXagyoJjSsn

Public key:02af0752af9d669a29cdddc6c625b8e66b0c81eacf37d7d47653bdd3dc7eaac786

Signature scheme:SHA256withECDSA

Create account successfully.

查看ONT钱包列表

./ontology account list

 

导入钱包

$ ./ontology account import -s walletfile.dat

交易转账

我创建了两个地址:

AMMWWMW77HTB1VyW6jdGu3utWxd78DZetA,ARMYgzbgo6rgWnToM7PPbQ5AbfiVv1aomQ

//查看余额

$ ./ontology asset balance 地址

 

可以看到他们的余额分别是:

接下来我们进行转账:

 

$ ./ontology asset transfer --from=AMMWWMW77HTB1VyW6jdGu3utWxd78DZetA --to=ARMYgzbgo6rgWnToM7PPbQ5AbfiVv1aomQ --amount=10 --asset=ont

 

$ ./ontology asset transfer --from=1 --to=2 --amount=10000 --asset=ont

 

详细参数明细请参考:https://github.com/ontio/ontology/blob/sharding/docs/specifications/cli_user_guide_CN.md#32-ontong%E8%BD%AC%E8%B4%A6

 

输入密码转账:

 

OK,转账成功了,它提示我们通过info status可以查看事务状态,那我们查看一下:

State 1表示交易成功,GasConsumed表示收取的ONG燃油,由于本地测试链默认为0,Notify输出日志。详细请参考:https://github.com/ontio/ontology/blob/sharding/docs/specifications/cli_user_guide_CN.md#42-%E6%9F%A5%E8%AF%A2%E4%BA%A4%E6%98%93%E4%BF%A1%E6%81%AF

 cli 使用说明:

https://github.com/ontio/ontology/blob/sharding/docs/specifications/cli_user_guide_CN.md

 

申请测试币

我们去官方申请测试币:https://developer.ont.io/applyOng

./ontology asset balance 

 

 

查看未解绑的ONG余额(空投)

./ontology asset unboundong <address|index|label>

提取未解绑的ONG余额

./ontology asset withdrawong <address|index|label>

测试:

/*
OEP-4
1、交易类型
2from
3to
4amount
 */
System.out.println(new String(Helper.hexToBytes("7472616e73666572")));
System.out.println(Address.parse("f54855d4e025d8f5b9f0ac1b2ae3c8171bb7fc17").toBase58());
System.out.println(Address.parse("623f867e72150c077729dbbcf32c3869b195e775").toBase58());
System.out.println(Helper.BigIntFromNeoBytes(Helper.hexToBytes("40b956012421")));

 

// OEP-5 Or OEP-8 游戏相关协议,复杂程度更高目前在用只有ONT自己的两个游戏实验项目。

 

创建合约

ERC-20、ERC-223、ERC-721(NEP-4、NEP-5、NEP-8)的区别

ERC-20与NEP-4对应,都是基础token标准,ERC-223与NEP-5对应都是升级token标准(允许合约-合约交易) ,ERC-721与NEP-8对应每份token都是唯一的,是一种物权所有权凭证标准,在游戏中应用更为广泛。

客户端配置

import com.comex.exceotion.ChainClientException;
import com.github.ontio.OntSdk;
import com.github.ontio.sdk.exception.SDKException;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * @program: comex-wallet
 * @description: ONT钱包客户端配置
 * @author: Mr.LMing.X
 * @create: 2019-11-22 18:34
 **/

@Slf4j
@Configuration
public class OntClientConfig {

    // 默认rpcUrl = http://182.61.12.9:20336
    @Value("${wallet.rpcUrl}")
    private String rpcUrl;

    @Bean
    public OntSdk getOntSdk() {
        OntSdk ontSdk;
        try {
            ontSdk = OntSdk.getInstance();
            ontSdk.setRpc(rpcUrl);
            ontSdk.setRestful("http://192.168.1.223:20334");
            ontSdk.setDefaultConnect(ontSdk.getRpc());
//            ontSdk.openWalletFile("wallet.dat");
        } catch (SDKException e) {
            log.error("获取ONT钱包客户端时发生异常 SDKException error:{}", e);
            throw new ChainClientException(e);
        } catch (Exception e) {
            log.error("获取ONT钱包客户端时发生异常 Exception error:{}", e);
            throw new ChainClientException(e);
        }
        return ontSdk;
    }
}

通过SDK创建钱包

注意保存私钥!!!

public void createAccount() throws Exception {
    com.github.ontio.account.Account acct = new com.github.ontio.account.Account(ontSdk.defaultSignScheme);
    //私钥
    System.out.println(Helper.toHexString(acct.serializePrivateKey()));
    //公钥
    System.out.println(Helper.toHexString(acct.serializePublicKey()));
    //base58地址
    System.out.println(acct.getAddressU160().toBase58());

    com.github.ontio.sdk.wallet.Account accountFromPriKey = ontSdk.getWalletMgr().createAccountFromPriKey("123456", Helper.toHexString(acct.serializePrivateKey()));

    System.out.println(accountFromPriKey.key);
    System.out.println(accountFromPriKey.isDefault);
    ontSdk.getWalletMgr().writeWallet();

    System.out.println("init size: " + ontSdk.getWalletMgr().getWallet().getAccounts().size() + " " + ontSdk.getWalletMgr().getWalletFile().getAccounts().size());
    System.out.println(ontSdk.getWalletMgr().getWallet().toString());
    System.out.println(ontSdk.getWalletMgr().getWalletFile().toString());

}

导出钱包文件

$ ./ontology account export ./export_wallet.dat

--wallet-w

指定导出钱包

--low-security

降低导出 Keystore 文件中的账户保护安全等级


在线IDE编写OEP-4合约

在线IDE:https://smartx.ont.io/

创建一个Python的OEP-4协议的合约:

 

 

OntCversion = '2.0.0'
"""
An Example of OEP-4
"""
from ontology.interop.System.Storage import GetContext, Get, Put, Delete
from ontology.interop.System.Runtime import Notify, CheckWitness
from ontology.interop.System.Action import RegisterAction
from ontology.builtins import concat
from ontology.interop.Ontology.Runtime import Base58ToAddress

TransferEvent = RegisterAction("transfer", "from", "to", "amount")
ApprovalEvent = RegisterAction("approval", "owner", "spender", "amount")

ctx = GetContext()

NAME = '冥币' // 代币名称
SYMBOL = 'MingB'  // 币种名称
DECIMALS = 8    // 精度
FACTOR = 100000000  //最小单位参考精度
OWNER = Base58ToAddress("AQf4Mzu1YJrhz9f3aRkkwSm9n3qhXGSh4p") // 合约所有者,默认合约的所有者为你所上传的钱包文件第一个账户,可以改
# OWNER = bytearray(b'\x61\x6f\x2a\x4a\x38\x39\x6f\xf2\x03\xea\x01\xe6\xc0\x70\xae\x42\x1b\xb8\xce\x2d')
TOTAL_AMOUNT = 1000000000   // 代币发行总量

// 下面则是一些默认的校验规则的定义了
BALANCE_PREFIX = bytearray(b'\x01')
APPROVE_PREFIX = b'\x02'
SUPPLY_KEY = 'TotalSupply'

// 一切调用的入口Main
def Main(operation, args):
//...省略内容,参考默认内容

// init 初始化方法,在创建完成之后需要进行调用,初始化发行量,所有者等信息
def init()
//...省略内容,参考默认内容

Name(),symbol(),decimals(),totalSupply()分别代表获取币种名称、币种、精度、总量

其他方法我们用到了在进行详细介绍,读者也可参考NEP-4协议说明:

ONT NEP-4详解

NEP-4 1.0版本

NEP-4 2.0版本

编译合约

我们通过右侧工具栏选择2.0版本,编译,编译成功后悔生成一串16进制的AVM字节码,导出成.avm文件,注意avm中如果有双引号请删除!

部署合约

客户端方式

 

./ontology contract deploy --code Ming.avm --name Ming --version 2.0.0 --author Ming --email 1611826890@qq.com --desc 命币 --gaslimit 30000000

--needstore:指定智能合约需要使用持久化的合约存储(默认不使用)。

--code:指定存储智能合约 AVM 字节码文件的路径。

--name:指定智能合约的名称。

--version:指定智能合约的版本号。

--author:指定智能合约的作者信息。

--email:指定智能合约的联系人电子邮件。

--desc:指定智能合约的描述信息。

--prepare, -p:指定智能合约的预部署。

响应:

Deploy contract:

  Contract Address:8b1c36e5b1c49d14fc46e0f27107f1c4575b4ef3

  TxHash:f0bd7cdfc0ac62b549364a6a78d236ab6fdc3877e751dbea7150bdea82ec742b

Java-SDK方式

InputStream is = new FileInputStream("/Users/sss/dev/ontologytest/IdContract/mingb.avm");

byte[] bys = new byte[is.available()];

is.read(bys);

is.close();

code = Helper.toHexString(bys);

ontSdk.setCodeAddress(Address.AddressFromVmCode(code).toHexString());

 

//部署合约,

Transaction tx = ontSdk.vm().makeDeployCodeTransaction(code, true, "MingB","v2.0", "Lming.X", "Lming@163.com","desp",

account.getAddressU160().toBase58(),ontSdk.DEFAULT_DEPLOY_GAS_LIMIT,500);

 

String txHex = Helper.toHexString(tx.toArray());

ontSdk.getConnect().sendRawTransaction(txHex);

//等待出块Thread.sleep(6000);

DeployCodeTransaction t = (DeployCodeTransaction) ontSdk.getConnect().getTransaction(txHex);

合约初始化

初始化我们通过sdk完成。

// 合约初始化
String sendInit = ontSdk.neovm().oep4().sendInit(acct1, acct1, 20000, 500);
System.out.println("\n sendInit------>" + sendInit);

// 参数:到账账户,支付账户,gaslimitgasprice

 

合约转账

数字货币和代币(Token)的区别

数字货币一般指一个区块链项目的平台代币,比如以太坊上的以太币,元界上的 ETP 都是基础代币。

而 Token 往往代表了一种资产,这些资产在已经存在的其他区块链之上运行,资产还可以像商品一样交易,例如消费积分、游戏虚拟资产。Token 离具体的区块链应用也会更近,因为区块链应用的项目方通常也是 Token 的发行方。

本体/以太坊账户模型

不同于UTXO账户模型,ONT借鉴了以太坊的账户模型。

第一类叫做合约账户 CA(Contracts Accounts),第二类叫做外部账户 EOA(Externally Owned Accounts)

简单理解就是:

CA 是智能合约代码用的账户,EOA 是人用的账户;所以 CA 可以存储并执行智能合约代码,它的智能被 EOA 激活,它也不保存和存储私钥,合约账户可以调用其他合约。

EOA 则是人们直接控制的账户,可以存储以太币,可以发送交易到合约账户,触发既定的逻辑。EOA 账户由公钥标识,由对应的私钥控制。

当合约账户被调用时,存储其中的智能合约可以在矿工处的虚拟机中自动执行,并消耗 Gas,如果 Gas 不足则会触发“Out of Gas”异常,被终止执行。

无论是 CA 还是 EOA,在以太坊内部都被看做状态对象(state objects),意思就是说这些账户都有自己的状态,EOA 具有以太币余额的状态,而 CA 除了余额,还多了合约存储状态。

ONT转账(EOA-> EOA)

Ont为整数,转账数量为实际数量。

// 地址:Aco8xpeQUaxsBN6BfEM4ykfkmaiGokMoyo
String privatekey3 = "38f9775c79d34cf2a2f82b6a4d2897d202ced260cfd20cc961760fa2864b15dd";
// 地址:AY9zGNmfNNBdNQT832JTfVMfm5BQ7bsaQ2
String privatekey4 = "ee9c45d357c9d75837e1acf4cb421581d1e72bacffe441b5b81d12444f707b4c";
// 地址: AauVpssPnwq6qwNz2nQME9VLjuxuvmEhEJ
String privatekey5 = "4e62ebe9650d160510e54333d5f9579e45428ce611fd0985088b08b4bdfb01b1";

Account caAcct3 = new com.github.ontio.account.Account(Helper.hexToBytes(privatekey3), ontSdk.defaultSignScheme);
Account caAcct4 = new com.github.ontio.account.Account(Helper.hexToBytes(privatekey4), ontSdk.defaultSignScheme);
Account oep4ContractAcct = new com.github.ontio.account.Account(Helper.hexToBytes(privatekey5), ontSdk.defaultSignScheme);

Transaction transaction = ontSdk.nativevm().ont().makeTransfer(oep4ContractAcct.getAddressU160().toBase58(), caAcct3.getAddressU160().toBase58(),
        100, oep4ContractAcct.getAddressU160().toBase58(), 20000, 500);

ontSdk.signTx(transaction, new Account[][]{{oep4ContractAcct}});

boolean b = ontSdk.getConnect().sendRawTransaction(transaction.toHexString());
System.out.println("\n ONT转账---->" + transaction.hash().toString() + " \n isSuccess---->" + b);

 

// 6cbbc353882d53403d1410b16a3908cd0823286539b05f6206c0a9e5067b4b6a

ONG转账(EOA-> EOA)

Ong精度9,转账时进行精度转换。

Long amount = new BigDecimal(30).multiply(BigDecimal.TEN.pow(9)).longValueExact();

Transaction transaction = ontSdk.nativevm().ong().makeTransfer(
        oep4ContractAcct.getAddressU160().toBase58(),
        caAcct3.getAddressU160().toBase58(),
        amount,
        oep4ContractAcct.getAddressU160().toBase58(),
        20000, 500);
ontSdk.signTx(transaction, new Account[][]{{oep4ContractAcct}});

boolean isSuccess = ontSdk.getConnect().sendRawTransaction(transaction.toHexString());
System.out.println("\n ONG转账】hash---->" + transaction.hash().toString() + " \n amount---->" + amount + " \n isSuccess---->" + isSuccess);

 

OEP-4合约账户向普通账户转账Token(CA -> EOA)

// 查询精度
int decimal = Integer.valueOf(ontSdk.neovm().oep4().queryDecimals());
Long amount = new BigDecimal(30).multiply(BigDecimal.TEN.pow(decimal)).longValue();
String from = oep4ContractAcct.getAddressU160().toBase58();
String to = caAcct3.getAddressU160().toBase58();
Transaction transaction = ontSdk.neovm().oep4().makeTransfer(
        from, to, amount, oep4ContractAcct,
        20000, 500);

ontSdk.signTx(transaction, new Account[][]{{oep4ContractAcct}});
boolean isSuccess = ontSdk.getConnect().sendRawTransaction(transaction.toHexString());
System.out.println("\n MingB Token转账】hash---->" + transaction.hash().toString()
        + " \n amount---->" + amount + " \n isSuccess---->" + isSuccess);

 

查看一下交易状态:

 

 

OEP-4外部账户向合约账户转账(EOA -> CA)

这里解释一下,如果一个外部账户向合约账户转账的是数字资产(ont/ong)则与不同转账并无区别。

如果是转账Token,那么用说 代币所有人账户 向 合约所有人账户 转账更加贴切,本质上合约所有人也是一个代币(Token)所有人。

System.out.println("\n " + oep4ContractAcct.getAddressU160().toBase58() + ": " + ontSdk.neovm().oep4().queryBalanceOf(caAcct3.getAddressU160().toBase58()));
System.out.println("\n " + oep4ContractAcct.getAddressU160().toBase58() + ": " + ontSdk.neovm().oep4().queryBalanceOf(caAcct4.getAddressU160().toBase58()));

String caToAcctToken = ontSdk.neovm().oep4().sendTransfer(caAcct3, caAcct4.getAddressU160().toBase58(), 10, oep4ContractAcct, 20000, 500);
System.out.println("\n EOA Token EOA---->" + caToAcctToken);

Thread.sleep(5000);

System.out.println("\n " + oep4ContractAcct.getAddressU160().toBase58() + ": " + ontSdk.neovm().oep4().queryBalanceOf(caAcct3.getAddressU160().toBase58()));
System.out.println("\n " + oep4ContractAcct.getAddressU160().toBase58() + ": " + ontSdk.neovm().oep4().queryBalanceOf(caAcct4.getAddressU160().toBase58()));

代币账户 -> 代币账户 Token(EOA -> EOA)

同上。

合约同时多笔转账

// com.github.ontio.core.asset.State;

// 合约多笔转账
// 需与states一一对应
Account[] accounts = new Account[]{oep4ContractAcct, oep4ContractAcct};
State[] states = new State[]{
        // 参数:fromtoamount
        new State(oep4ContractAcct.getAddressU160(), caAcct3.getAddressU160(), 10000),
        new State(oep4ContractAcct.getAddressU160(), caAcct4.getAddressU160(), 20000)
};


String transferMulti = ontSdk.neovm().oep4().sendTransferMulti(accounts, states, oep4ContractAcct, 20000, 500);
System.out.println("\n 合约多笔转账---->" + transferMulti);

 

查询区块所在高度

SDK:ontSdk.getConnect().getBlockHeightByTxHash("txhash")

HTTP:http://182.61.12.9:20334//api/v1/block/height/txhash/

Cli:./ontology info tx <txhash>

 

 

 

Logo

权威|前沿|技术|干货|国内首个API全生命周期开发者社区

更多推荐