001package org.consensusj.ethereum.jsonrpc;
002
003import org.consensusj.jsonrpc.DefaultRpcClient;
004import org.consensusj.jsonrpc.JsonRpcMessage;
005import org.consensusj.jsonrpc.JsonRpcStatusException;
006
007import java.io.IOException;
008import java.math.BigInteger;
009import java.net.URI;
010
011/**
012 * A partial implementation of an Ethereum RPC Client
013 *
014 * How to mine just a little for "reg test mode" in Eth:
015 * https://github.com/ethereum/go-ethereum/wiki/bitchin-tricks
016 * See also:
017 * https://github.com/ethereum/go-ethereum/wiki/Management-APIs
018 */
019public class EthereumClient extends DefaultRpcClient {
020    public static final URI DEFAULT_LOCALHOST = URI.create("http://localhost:8545");
021    
022    /**
023     * Construct a JSON-RPC client from URI, username, and password
024     *
025     * @param server      server URI should not contain username/password
026     * @param rpcuser     username for the RPC HTTP connection
027     * @param rpcpassword password for the RPC HTTP connection
028     */
029    public EthereumClient(URI server, String rpcuser, String rpcpassword) {
030        super(JsonRpcMessage.Version.V2, server, rpcuser, rpcpassword);
031    }
032
033    public EthereumClient() {
034        this(DEFAULT_LOCALHOST, null, null);
035    }
036    
037    public String ethProtocolVersion() throws IOException, JsonRpcStatusException {
038        return this.send("eth_protocolVersion");
039    }
040
041    public long ethBlockNumber() throws IOException, JsonRpcStatusException {
042        String blockNumString = this.send("eth_blockNumber");
043        long blockNum = Long.decode(blockNumString);
044        return blockNum;
045    }
046
047    public BigInteger ethGetBalance(String address, String block) throws IOException, JsonRpcStatusException {
048        String weiAsHexString = this.send("eth_getBalance", address, block);
049        return quantityToInt(weiAsHexString);
050    }
051
052    public String ethCall(EthTxCallObject callObject, String block) throws IOException, JsonRpcStatusException {
053        String data = this.send("eth_call", callObject, block);
054        return data;
055    }
056
057    public String web3ClientVersion() throws IOException, JsonRpcStatusException {
058        return this.send("web3_clientVersion");
059    }
060
061    /**
062     * Returns Keccak-256 (not the standardized SHA3-256) of the given data
063     * @param dataToHash
064     * @return Keccak-256 hash of the data
065     * @throws IOException
066     * @throws JsonRpcStatusException
067     */
068    public String web3Sha3(String dataToHash) throws IOException, JsonRpcStatusException {
069        return this.send("web3_sha3", dataToHash);
070    }
071
072    public boolean minerStart(int numberOfThreads) throws IOException, JsonRpcStatusException {
073        return this.send("miner_start", "0x" + Integer.toHexString(numberOfThreads));
074    }
075
076    public boolean minerStop() throws IOException, JsonRpcStatusException {
077        return this.send("miner_stop");
078    }
079
080    private BigInteger quantityToInt(String weiAsHexString) {
081        return new BigInteger(weiAsHexString.substring(2), 16);
082    }
083}