Bitcoinjs-lib: How to unlock p2pkh

Created on 26 Apr 2018  路  8Comments  路  Source: bitcoinjs/bitcoinjs-lib

I'm new to using this library and constructing Bitcoin transactions in general so sorry if this is obvious.

I have been sent Bitcoin from a testnet faucet as can be seen here: txid: d9c9213136854a53211f1c80d202b743dfe971867558fd2c5628fe781a7f7ba9

Everytime I try and broadcast the transaction on blockcypher I get this error

Error validating transaction: Error running script for input 0 referencing d9c9213136854a53211f1c80d202b743dfe971867558fd2c5628fe781a7f7ba9 at 0: Script was NOT verified successfully..

Generating the address:

function generateAddress(mnemonic) {
    var seed = bip39.mnemonicToSeed(mnemonic)
    var root = bitcoin.HDNode.fromSeedBuffer(seed, bitcoin.networks.testnet)
    var child = root.derivePath("m/44'/1'/0'/0/0")
    var address = child.getAddress() // mpxhLRAzfGc6tH55kzG9NfZ3b2VZdo3Gq9
    return address
}

Generate transaction:

function send(mnemonic) {
    var seed = bip39.mnemonicToSeed(mnemonic)
    var root = bitcoin.HDNode.fromSeedBuffer(seed, bitcoin.networks.testnet)
    var child = root.derivePath("m/44'/1'/0'/0/0")
    var change = root.derivePath("m/44'/1'/0'/1/0")

    var txb = new bitcoin.TransactionBuilder(bitcoin.networks.testnet)
    txb.addInput("d9c9213136854a53211f1c80d202b743dfe971867558fd2c5628fe781a7f7ba9", 0)
    txb.addOutput(change.getAddress(), 100)
    txb.sign(0, child.keyPair)
    console.log(txb.build().toHex())
}

Here is the transaction hex if you are interested:

0100000001a97b7f1a78fe28562cfd58758671e9df43b702d2801c1f21534a85363121c9d9000000006a47304402202c142f548c830a2d1176fc4b296f85258bade9236f813add6a379a65ea09641302201e3bf5b91ae5b7b917287b174459131738345195cd262988164c7eb33b169c0c012103ee17f1f4b65794c05a67612ead47173884d22062c8150e1863ba5709b12a9ed5ffffffff0164000000000000001976a914acfc0a57a25500052cb20026ae994565cd43927b88ac00000000

I don't see where I am going wrong but if I had to guess it has something to do with the script type (pay-to-pubkey-hash) hence the title of this issue.

how to / question / docs

Most helpful comment

@afk11 maybe it should:

  • enforce no duplicate whitespace
  • enforce non-zero length
  • enforce only printable characters

I have had each of those burn me in the past, and nearly experienced fund loss in a duplicate whitespace case.

All 8 comments

public key from tx:
pubkey: 03ee17f1f4b65794c05a67612ead47173884d22062c8150e1863ba5709b12a9ed5
pubkeyhash: b14b7ce2356525db27768f05b2f5cc7d9b55613c
address: mwgQKzcarE896qnUrr1tZ9WqphnBJwi4rp

output 0 on blockcypher
address: mpxhLRAzfGc6tH55kzG9NfZ3b2VZdo3Gq9

Child must be the wrong private key? You're probably running into this line of code, which just initializes the input for that key.. https://github.com/bitcoinjs/bitcoinjs-lib/blob/master/src/transaction_builder.js#L352

Print out the public key or address for a few of the keys once again to check if your bip32 path is correct.

The child in generateAddress is mpxhLRAzfGc6tH55kzG9NfZ3b2VZdo3Gq9 which is expected.
The child in send is mwgQKzcarE896qnUrr1tZ9WqphnBJwi4rp which was not expected.

It seems like the output for root.derivePath("m/44'/1'/0'/0/0") is different the second time I called it and I was expecting it to be the same. Is this normal behaviour? And if it is do you mind explaining why it does this?

I successfully broadcasted the transaction

The problem I had was that I forgot to pass the mnemonic to the function and that took me way longer to see than it ought to.

It happens, glad to gear you got it sorted!

The problem I had was that I forgot to pass the mnemonic to the function and that took me way longer to see than it ought to.

Why didn't it throw?

edit: https://github.com/bitcoinjs/bip39/blob/bafbcd352a6a5275bbc640a79c3917d0baee5bc8/index.js#L50 ... oh, I'll change that.

https://github.com/bitcoinjs/bip39/issues/77

hmm, oh yea, that stuff :/ I never think to check the input to the normalization.. extra whitespace between two of the words can lead to similar confusion, as it's directly input to a hash function.

@afk11 maybe it should:

  • enforce no duplicate whitespace
  • enforce non-zero length
  • enforce only printable characters

I have had each of those burn me in the past, and nearly experienced fund loss in a duplicate whitespace case.

Yea I totally agree. Pretty sure this is repeated across the ecosystem, so probably a worth while effort :P

Was this page helpful?
0 / 5 - 0 ratings

Related issues

panpan2 picture panpan2  路  3Comments

coingeek picture coingeek  路  4Comments

rbndg picture rbndg  路  3Comments

silence-may picture silence-may  路  3Comments

dcousens picture dcousens  路  3Comments