diff --git a/src/transaction_builder.js b/src/transaction_builder.js index 8706841..b00871d 100644 --- a/src/transaction_builder.js +++ b/src/transaction_builder.js @@ -633,6 +633,8 @@ TransactionBuilder.prototype.sign = function (vin, keyPair, redeemScript, hashTy // TODO: remove keyPair.network matching in 4.0.0 if (keyPair.network && keyPair.network !== this.network) throw new TypeError('Inconsistent network') if (!this.__inputs[vin]) throw new Error('No input at index: ' + vin) + if (this.__needsOutputs()) throw new Error('Transaction needs outputs') + hashType = hashType || Transaction.SIGHASH_ALL const input = this.__inputs[vin] @@ -694,8 +696,7 @@ function signatureHashType (buffer) { TransactionBuilder.prototype.__canModifyInputs = function () { return this.__inputs.every(function (input) { - // any signatures? - if (input.signatures === undefined) return true + if (!input.signatures) return true return input.signatures.every(function (signature) { if (!signature) return true @@ -708,6 +709,20 @@ TransactionBuilder.prototype.__canModifyInputs = function () { }) } +TransactionBuilder.prototype.__needsOutputs = function () { + // if any signature is not SIGHASH_NONE, + // we need outputs + return (this.__tx.outs.length === 0) && this.__inputs.some(function (input) { + if (!input.signatures) return false + + return input.signatures.some(function (signature) { + if (!signature) return false + const hashType = signatureHashType(signature) + return ~(hashType & Transaction.SIGHASH_NONE) + }) + }) +} + TransactionBuilder.prototype.__canModifyOutputs = function () { const nInputs = this.__tx.ins.length const nOutputs = this.__tx.outs.length diff --git a/test/fixtures/transaction_builder.json b/test/fixtures/transaction_builder.json index 6896f30..4cc7e85 100644 --- a/test/fixtures/transaction_builder.json +++ b/test/fixtures/transaction_builder.json @@ -2336,6 +2336,22 @@ "value": 1000 } ] + }, + { + "description": "Transaction w/ no outputs", + "exception": "Transaction needs outputs", + "inputs": [ + { + "txId": "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff", + "vout": 0, + "signs": [ + { + "keyPair": "KwDiBf89QgGbjEhKnhXJuH7LrciVrZi3qYjgd9M7rFU73sVHnoWn" + } + ] + } + ], + "outputs": [] } ], "fromTransaction": [ diff --git a/test/transaction_builder.js b/test/transaction_builder.js index 4ebd73d..aec2450 100644 --- a/test/transaction_builder.js +++ b/test/transaction_builder.js @@ -289,6 +289,7 @@ describe('TransactionBuilder', function () { it('throws if if there exist any scriptSigs', function () { const txb = new TransactionBuilder() txb.addInput(txHash, 0) + txb.addOutput(scripts[0], 100) txb.sign(0, keyPair) assert.throws(function () {