BTC转账(BIP39)

public class BitUtil {
    public static Object signBTCTransactionData(List unSpentBTCList, WalletModel walletModel, String to, long value, long fee) throws Exception {
        NetworkParameters networkParameters = Getnetparams.GetNetworkParams();
        Transaction transaction = new Transaction(networkParameters);
        long totalMoney = 0;
        List utxos = new ArrayList<>();
        long myfee = 34*2+10;
        long halfHourFee  = Long.parseLong(JSONObject.parseObject(HttpUtils.sendGet("https://bitcoinfees.earn.com/api/v1/fees/recommended","")).getString("hourFee"));
//        System.out.println(jsStr.getString("halfHourFee"));
        long Input = 0;
        long transfee=0;
        for (UnSpentBTC us : unSpentBTCList) {
            if (totalMoney >= value + (myfee+ Input * 148)*halfHourFee) {
                transfee = (myfee+ Input * 148)*halfHourFee;
                break;
            }
            UTXO utxo = new UTXO(Sha256Hash.wrap(us.getTxid()), us.getVout(), Coin.valueOf(us.getSatoshis()),
                    us.getHeight(), false, new Script(Hex.decode(us.getScriptPubKey())));
            utxos.add(utxo);
            totalMoney += us.getSatoshis();
            Input++;
        }
        transaction.addOutput(Coin.valueOf(value), Address.fromBase58(networkParameters, to));
        // transaction.
        //消费列表总金额 - 已经转账的金额 - 手续费 就等于需要返回给自己的金额了
        long balance = totalMoney - value - ((myfee+ Input * 148)*halfHourFee);
        //输出-转给自己
        if (balance > 0) {
            transaction.addOutput(Coin.valueOf(balance), Address.fromBase58(networkParameters, walletModel.getAddress()));
        }
        //输入未消费列表项
        for (UTXO utxo : utxos) {
            TransactionOutPoint outPoint = new TransactionOutPoint(networkParameters, utxo.getIndex(), utxo.getHash());
            DeterministicKey key = AddressUtils.getDeterministicKey(walletModel.getSeedCode(), walletModel.getPassphrase(), walletModel.getKeyPath());
            transaction.addSignedInput(outPoint, ScriptBuilder.createOutputScript(new Address(networkParameters, key.getPubKeyHash())), key, Transaction.SigHash.ALL, true);
        }

        Cardetails cardetails = new Cardetails(transaction.getHash().toString(),Hex.toHexString(transaction.bitcoinSerialize()),Long.toString(transfee));

        return cardetails;
    }


}

Cardetails 是我定义的一个类获得hash和rawcode还有fee传出去

 

可能会有人疑问手续费为什么这么算的 ,大家可参考这一篇文章BTC手续费计算

List是我从RPC获取的UTXO自己构造的

WalletModel 是一个根据助记词生成BIP39的私钥和地址的类,可以做多币种, 大家可以自己写或者参考HD钱包的

附带上pib助记词生成校验网址BIP

助记词如何生成可以参考我写的这个

public class MnemonicUtil {
    /**
     * 生成12个助记词
     *
     * @return
     * @throws IOException
     * @throws MnemonicException.MnemonicLengthException
     */
    public static List getWordList() throws IOException, MnemonicException.MnemonicLengthException {
        MnemonicCode mnemonicCode = new MnemonicCode();
        SecureRandom secureRandom = new SecureRandom();
        /**必须是被4整除*/
        byte[] initialEntropy = new byte[16];
        secureRandom.nextBytes(initialEntropy);
        return mnemonicCode.toMnemonic(initialEntropy);
    }
}
 @Test
        public void RandAccount() throws Exception {
                //随机生成助记词 根据助记词生成各个地址。切记要记住助记词
                List mnemonicList = MnemonicUtil.getWordList();
                String MyMnemonic = StringUtils.join(mnemonicList," ");
                System.out.println(MyMnemonic);
}

 

记得pom导入bitcoinj14版本

你可能感兴趣的:(区块链,Java)