java和android如何使⽤web3j开发以太坊智能合约并进⾏交易
教程
从⼴义上讲,有web3j⽀持三种类型的以太坊交易:
1.以太币从⼀⽅交易到另⼀⽅
2.创建⼀个智能合约
3.与智能合约交易
为了进⾏这些交易,必须有以太币(以太坊区块链的)存在于交易发⽣的以太坊账户中。这是为了⽀付成本,这是为⽀付参与交易的以太坊客户端的交易执⾏成本,⽀付了这个成本就能将结果提交到以太坊区块链上。获得以太币的说明下⽂会说到。
此外,我们还可以查询智能合约的状态。
image
如何获得以太币Ether
要想获得以太币Ether你有两种途径可以选择:
1.⾃⼰开采挖矿
2.从别⼈那⾥获取以太币
在私有链中⾃⼰挖矿,或者公共测试链(testnet)是⾮常简单直接的。但是,在主要的公有链(mainnet)中,它需要很多很明显的专⽤GPU时间,除⾮你已经拥有多个专⽤GPU的矿机,否则基本上不太可⾏。如果你希望使⽤私有链,则在这个中有⼀些指导。
要购买以太币Ether,你需要通过交易所。由于不同的地区有不同的交易所,你还需要研究⾃⼰去哪⼉合适。中包含多个交易所,是⼀个很好的参考。
以太坊测试链(testnets)
针对Ethereum以太坊有许多专⽤测试⽹络或者叫测试链,他们由各种客户端⽀持。
1.Rinkeby:只⽀持geth客户端。
2.Kovan:只⽀持Parity客户端。
3.Ropsten:⽀持geth和Parity客户端。
对于开发,建议你使⽤Rinkeby或KoVan测试链。这是因为他们使⽤的⼯作量证明POA共识机制,确保交易和块能够⼀致并及时的创
建。Ropsten测试链,虽然最接近公有链(Mainnet),但是因为它使⽤的⼯作量证明是POW共识机制,过去已受到攻击,对以太坊开发⼈员来说往往有更多的问题。
有关如何请求Kovan测试链的细节可以在到。
如果你需要在Ropsten上的得到⼀些以太币,将你的钱包地址的消息发布到,然后会发送⼀些给你。
在testnet测试链或者私有链上挖掘
在ethereum以太坊测试链testnet中,挖掘难度低于公有链mainnet。这意味着你可以⽤普通的CPU,⽐如你的笔记本电脑来挖掘新的以太币。你需要做的是运⾏⼀个以太坊客户端,例如geth或Parity,开始做⼀些储备。进⼀步的资料可在他们的官⽅⽹站上获得。
geth :
Parity :
⼀旦你开采了⼀些以太币,你就可以开始使⽤以太坊区块链了。
然⽽,如上所述,使⽤Kovan或者Rinkeby测试⽹络更简单些。
gas
当在Ethereum以太坊发⽣交易时,必须为执⾏该交易的客户端⽀付交易成本,将该交易的输出提交到以太坊区块链Ethereum blockchain。
此成本是通过gas来测量的,其中gas是⽤于在以太坊虚拟机中执⾏交易指令的数量。请参阅以获取更多信息。
当你使⽤以太坊客户端时,这意味着,有两个参数⽤来指⽰你希望花费多少以太来完成传输:
gas price :⽓体价格,这是每单位gas中以太的消耗量。Web3j使⽤的默认价格为22000000000 wei(22×10-8 Ether)。这是在中定义的。
gas limit:⽓体最⼤量,这是你愿意在交易执⾏上花费的gas的最⼤总量。单个交易在⼀个以太坊区块中有多⼤的上限,通常将该值限制为⼩于6700000。当前的gas限制在这⾥查。
这两个参数共同决定了你愿意花费在交易成本上的最⼤量的以太币Ether。也就是说,你花费的gas不会超过gas price * gas limit。gas价格也会影响交易发⽣的速度,这取决于其他交易是否能为矿⼯提供更有利的gas价格。
你可能需要调整这些参数以确保交易能及时进⾏。
交易机制
当你⽤⼀些以太币Ether创建了⼀个有效的帐户时,你可以使⽤两种机制来与以太坊进⾏交易。
通过以太坊ethereum客户端进⾏认证签名交易
离线交易签名认证
这两种机制都是Web3j所⽀持的。
通过以太坊ethereum客户端进⾏认证签名交易
为了通过以太坊客户端进⾏交易,⾸先需要确保你正在使⽤的客户端知道你的钱包地址。最好是运⾏⾃⼰的以太坊客户端,⽐
如geth/Parity,以便可以更⽅便的做到这⼀点。⼀旦你有⼀个客户端运⾏,你可以创建⼀个以太坊钱包,通过:
包含了geth⽀持的良好运⾏的不同机制,例如导⼊私有密钥⽂件,并通过控制台创建新的以太坊帐户。
或者,你可以通过客户端使⽤JSON-RPC管理命令,例如⽤personal_newAccount为geth/Parity创建新以太坊账户。
通过创建你的钱包⽂件,你可以通过web3j打开帐户,⾸先创建⽀持geth/Parity管理命令的web3j实例:
Admin web3j = Admin.build(new HttpService());
然后,你可以解锁帐户,并如果是成功的,就可以发送⼀个交易:
PersonalUnlockAccount personalUnlockAccount = web3j.personalUnlockAccount("", "a password").send();
if (personalUnlockAccount.accountUnlocked()) {
// send a transaction
}
以这种⽅式发送的交易应该通过创建,使⽤类型:
Transaction transaction = ateContractTransaction(
<from address>,
<nonce>,
BigInteger.valueOf(<gas price>), // we use default gas limit
"0x...<smart contract code to execute>"
);
org.sponse.EthSendTransaction
transactionResponse = hSendTransaction(ethSendTransaction)
.send();
String transactionHash = TransactionHash();
// poll for transaction response via org.web3j.hGetTransactionReceipt(<txHash>)
其中nonce值获得⽅式,下⽂会提到。
有关此交易⼯作流的详细信息,请参阅和。
web3j⽀持的各种管理命令的进⼀步细节在中。
离线交易签名认证Offline transaction signing
如果你不想管理⾃⼰的以太坊客户端,或者不想向以太坊客户端提供诸如密码之类的钱包详细信息,那么就通过离线交易认证签名。
离线交易签名认证允许你在web3j中使⽤你的以太坊钱包签署交易,允许你完全控制你的私有凭据。然后,离线创建的交易可以被发送到⽹络上的任何以太坊客户端,只要它是⼀个有效的交易,它会将交易传播到其他节点。
如果需要,还可以执⾏进程外交易签名认证。这可以通过重写的sign⽅法来实现。
创建和使⽤钱包⽂件Ethereum wallet file
为了离线脱机交易,你需要有你的钱包⽂件或与私密钱包/账户相关的公共和私⼈密钥。
web3j能够为你⽣成⼀个新的安全的以太坊钱包⽂件Ethereum wallet file,或者与也可以通过私钥来和现有的钱包⽂件⼀起⼯作。
创建新的钱包⽂件:
String fileName = ateNewWalletFile(
"your password",
new File("/path/to/destination"));
加载凭据从钱包⽂件:
Credentials credentials = WalletUtils.loadCredentials(
"your password",
"/path/to/walletfile");
然后这些凭据会被⽤来签署交易,请参阅Web3安全存储定义钱包⽂件规范
签署以太坊交易
要使脱机签名交易得到签署,需要设定⼀个类型。RawTransaction类似于前⾯提到的Transaction类型,但是它不需要通过具体的账号地址来请求,因为可以从签名中推断出来。
为了创建和签署原⽣交易,交易的顺序如下:
1.确定交易发起者帐户的下⼀个可⽤随机数nonce
2.创建RawTransaction对象
3.使⽤递归长度前缀编码(RLP即)对RawTransaction对象进⾏编码
4.签署RawTransaction对象
5.将RawTransaction对象发送到节点进⾏处理
nonce是⼀个不断增长的数值,⽤来唯⼀地标识交易。⼀个nonce只能使⽤⼀次,直到交易被挖掘完成,可以以相同的随机数发送交易的多个版本,但是⼀旦其中⼀个被挖掘完成,其他后续提交的都将被拒绝。
⼀旦获得下⼀个可⽤的nonce,该值就可以⽤来创建transaction对象:
RawTransaction rawTransaction = ateEtherTransaction(
nonce, <gas price>, <gas limit>, <toAddress>, <value>);
然后可以对交易进⾏签名和编码:
byte[] signedMessage = TransactionEncoder.signMessage(rawTransaction, <credentials>);
String hexValue = HexString(signedMessage);
其中凭据是根据加载的。
然后使⽤发送交易:
EthSendTransaction ethSendTransaction = hSendRawTransaction(hexValue).sendAsync().get();
String transactionHash = TransactionHash();
// poll for transaction response via org.web3j.hGetTransactionReceipt(<txHash>)
有关创建和发送原始事务的完整⽰例,请参阅。
交易随机数nonce
nonce是⼀个不断增长的数值,⽤来唯⼀地标识交易。⼀个nonce只能使⽤⼀次,直到交易被挖掘完成,可以以相同的随机数发送交易的多个版本,但是⼀旦其中⼀个被挖掘完成,其他后续提交的都将被拒绝。
可以通过eth_getTransactionCount⽅法获得下⼀个可⽤的nonce:
EthGetTransactionCount ethGetTransactionCount = hGetTransactionCount(
address, DefaultBlockParameterName.LATEST).sendAsync().get();
BigInteger nonce = TransactionCount();
然后可以使⽤nonce创建你的交易对象:
RawTransaction rawTransaction = ateEtherTransaction(
nonce, <gas price>, <gas limit>, <toAddress>, <value>);
交易类型
web3j中的不同类型的交易都使⽤Transaction和RawTransaction对象。关键的区别是交易对象必须始终有⼀个地址,以便处
理eth_sendTransaction请求的以太坊客户端知道要使⽤哪个钱包来代表消息发送者并发送该交易。如上所述,对于离线签名认证签署的原始交易⽽⾔,这不是必须的。
接下来的部分概述了不同交易类型所需的关键交易属性。下列属性对所有⼈都是不变:
Gas price 天然⽓⽓体价格
Gas limit 天然⽓⽓体限制
Nonce 随机数
from 发送地址
Transaction和RawTransaction对象在所有后续⽰例中都可互换使⽤。
以太币从⼀⽅交易到另⼀⽅
在双⽅之间发送以太币Ether需要交易对象的最少量的信息:
to :⽬的地钱包地址
value:价值,希望发送到⽬的地的以太币数量
BigInteger value = Wei("1.0", Convert.Unit.ETHER).toBigInteger();
RawTransaction rawTransaction = ateEtherTransaction(
<nonce>, <gas price>, <gas limit>, <toAddress>, value);
//
但是,建议你使⽤来发送以太币Ether,它负责对nonce管理和通过不断的轮询为你提供响应:
Web3j web3 = Web3j.build(new HttpService()); // defaults to localhost:8545/
Credentials credentials = WalletUtils.loadCredentials("password", "/path/to/walletfile");
TransactionReceipt transactionReceipt = Transfer.sendFunds(
web3, credentials, "0x<address>|<ensName>",
android学习教程
BigDecimal.valueOf(1.0), Convert.Unit.ETHER).send();
使⽤智能合约打包器smart contract wrappers
当使⽤下⾯列出的智能合约打包器时,将不得不⼿动执⾏从Solidity到本机Java类型的所有转换。使⽤是⾮常有效的,它负责所有的代码⽣成和转换。
创建⼀个智能合约
要部署新的智能合约,需要提供以下属性:
value :在智能合约中希望存放的以太坊Ether量(如果没有提供默认为零)
data :⼗六进制格式化、编译的智能合约创建代码
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论