記事の内容
web3jを使ってsolidityで作成したコントラクトを実行する方法です。
solファイルをJavaのクラスに変換する方法についてはこちらをご確認ください。
本記事で使用するコントラクトは以下の記事に記載の内容を使用します。
solidityのコントラクトをJavaのコントラクトクラスに変換する方法
コード
try {
SampleGasProvider gasProvider = new SampleGasProvider(BigInteger.valueOf(500), BigInteger.valueOf(200000));
Addition contract = Addition.deploy(
web3j,
credentials,
gasProvider
).send();
// コントラクトのアドレスを出力
System.out.println("contract address: " + contract.getContractAddress());
// メソッド呼び出し(トランザクションなし)
System.out.println("get: " + contract.get().send());
System.out.println("add: " + contract.add(BigInteger.valueOf(10)).sendAsync());
System.out.println("get: " + contract.get().send());
} catch (Exception e) {
e.printStackTrace();
}
package jp.ethereum;
import java.math.BigInteger;
import org.web3j.tx.gas.ContractGasProvider;
public class SampleGasProvider implements ContractGasProvider{
private BigInteger gasPrice;
private BigInteger gasLimit;
public SampleGasProvider(BigInteger gasPrice, BigInteger gasLimit) {
this.gasPrice = gasPrice;
this.gasLimit = gasLimit;
}
@Override
public BigInteger getGasPrice(String contractFunc) {
return this.gasPrice;
}
@Override
public BigInteger getGasPrice() {
return this.gasPrice;
}
@Override
public BigInteger getGasLimit(String contractFunc) {
return this.gasLimit;
}
@Override
public BigInteger getGasLimit() {
return this.gasLimit;
}
}
コードの内容は単純です。
まずは、コントラクトをデプロイします。
この処理が終わると、コントラクトをデプロイ用のトランザクションが作成され、ブロックに取り込まれた後に処理が完了します。
Addition contract = Addition.deploy(
web3j,
credentials,
gasProvider
).send();
実行結果(gethコンソール)
INFO [09-16|17:19:41.983] Submitted contract creation fullhash=0xd169416410c2e6e7bdc02a2a27384ed2425e1433f39117a3810675fcfed85353 contract=0xf5ad7542173e8944D1aE16B4394eAA34cfdA4814
次にコントラクトを実行します。
System.out.println("get: " + contract.get().send());
System.out.println("add: " + contract.add(BigInteger.valueOf(10)).sendAsync());
この例ではコントラクトのget処理をまずは呼び出します。
getは値を参照するだけなのでトランザクションは作成されず、すぐに応答が返ってきます。
次のadd処理は値を更新する処理なのでトランザクションが作成されます。
「sendAsync」を使用しているため、ブロックに取り込まれる前に応答が返ってきます。
この例だと以下のような出力になります。
add: java.util.concurrent.CompletableFuture@18271936[Not completed]
ブロックに取り込まれるまで処理を待つ必要がある場合は、以下のとおり変更します。
System.out.println("add: " + contract.add(BigInteger.valueOf(10)).send());
コントラクトのロード
上述したコードはコントラクトをデプロイして実行するという方法でしたが、既にデプロイ済みのコントラクトを実行する方法もあります。
Addition contract = Addition.load(
address,
web3j,
credentials,
gasProvider
);
デプロイと引数はほとんど変わりませんが、第一引数にコントラクトのアドレスが入ります。(0xを含む)
それ以降の操作は全く変わりません。