add merge options

This commit is contained in:
Matias Alejo Garcia 2014-04-13 09:49:26 -03:00
parent 233438f899
commit 9a25122b4f
2 changed files with 89 additions and 17 deletions

View File

@ -830,9 +830,9 @@ TransactionBuilder.prototype._checkMergeability = function(b) {
// this assumes that the same signature can not be v0 / v1 (which shouldnt be!) // this assumes that the same signature can not be v0 / v1 (which shouldnt be!)
TransactionBuilder.prototype._mergeInputSig = function(s0buf, s1buf) { TransactionBuilder.prototype._mergeInputSig = function(s0buf, s1buf, ignoreConflictingSignatures) {
if (buffertools.compare(s0buf,s1buf) === 0) { if (buffertools.compare(s0buf,s1buf) === 0) {
console.log('BUFFERS .s MATCH'); //TODO //console.log('BUFFERS .s MATCH'); //TODO
return s0buf; return s0buf;
} }
// Is multisig? // Is multisig?
@ -874,19 +874,24 @@ TransactionBuilder.prototype._mergeInputSig = function(s0buf, s1buf) {
} }
} }
if (emptySlots.length<diff.length) if (emptySlots.length<diff.length) {
throw new Error('no enough empty slots to merge Txs'); if (!ignoreConflictingSignatures) {
throw new Error(
for (var i=0; i<diff.length; i++) { 'no enough empty slots to merge Txs: Check ignoreConflictingSignatures option');
s0.chunks[emptySlots[i]] = diff[i]; }
this.signaturesAdded++; }
else {
for (var i=0; i<diff.length; i++) {
s0.chunks[emptySlots[i]] = diff[i];
this.signaturesAdded++;
}
s0.updateBuffer();
} }
s0.updateBuffer();
return s0.getBuffer(); return s0.getBuffer();
}; };
TransactionBuilder.prototype._mergeTx = function(tx) { TransactionBuilder.prototype._mergeTx = function(tx, ignoreConflictingSignatures) {
var v0 = this.tx; var v0 = this.tx;
var v1 = tx; var v1 = tx;
@ -905,14 +910,14 @@ TransactionBuilder.prototype._mergeTx = function(tx) {
if (buffertools.compare(i0.o,i1.o) !== 0) if (buffertools.compare(i0.o,i1.o) !== 0)
throw new Error('TX .o in mismatch in merge. Input:',i); throw new Error('TX .o in mismatch in merge. Input:',i);
i0.s=this._mergeInputSig(i0.s,i1.s); i0.s=this._mergeInputSig(i0.s,i1.s, ignoreConflictingSignatures);
if (v0.isInputComplete(i)) this.inputsSigned++; if (v0.isInputComplete(i)) this.inputsSigned++;
} }
}; };
TransactionBuilder.prototype.merge = function(b) { TransactionBuilder.prototype.merge = function(b, ignoreConflictingSignatures) {
this._checkMergeability(b); this._checkMergeability(b);
@ -922,7 +927,7 @@ TransactionBuilder.prototype.merge = function(b) {
!== b.tx.getNormalizedHash().toString('hex')) !== b.tx.getNormalizedHash().toString('hex'))
throw new Error('mismatch at TransactionBuilder NTXID'); throw new Error('mismatch at TransactionBuilder NTXID');
this._mergeTx(b.tx); this._mergeTx(b.tx, ignoreConflictingSignatures);
// TODO UPDATE: signaturesAdded, inputsSigned // TODO UPDATE: signaturesAdded, inputsSigned
} }
}; };

View File

@ -757,8 +757,78 @@ describe('TransactionBuilder', function() {
b5.signaturesAdded.should.equal(3); b5.signaturesAdded.should.equal(3);
}); });
it('#merge self', function() {
var b = getBuilder3([{
address: 'mrPnbY1yKDBsdgbHbS7kJ8GVm8F66hWHLE',
amount: 16
}])
.sign(testdata.dataUnspentSign.keyStrings);
b.merge(b);
it('#merge p2sh/p2pubkeyhash', function() { b.isFullySigned().should.equal(true);
var tx = b.build();
tx.isComplete().should.equal(true);
tx.ins.length.should.equal(3);
tx.outs.length.should.equal(2);
});
it('#merge simple', function() {
var b = getBuilder3([{
address: 'mrPnbY1yKDBsdgbHbS7kJ8GVm8F66hWHLE',
amount: 16
}])
.sign(testdata.dataUnspentSign.keyStrings);
// merge simple
var b2 = getBuilder3([{
address: 'mrPnbY1yKDBsdgbHbS7kJ8GVm8F66hWHLE',
amount: 16
}]);
b2.isFullySigned().should.equal(false);
b2.merge(b);
b2.isFullySigned().should.equal(true);
var tx = b.build();
tx.isComplete().should.equal(true);
tx.ins.length.should.equal(3);
tx.outs.length.should.equal(2);
});
it('#merge checks', function() {
var b = getBuilder3([{
address: 'mrPnbY1yKDBsdgbHbS7kJ8GVm8F66hWHLE',
amount: 16
}]);
// bad amount
var b2 = getBuilder3([{
address: 'mrPnbY1yKDBsdgbHbS7kJ8GVm8F66hWHLE',
amount: 15
}]);
(function() {b2.merge(b);}).should.throw();
// bad out
b2 = getBuilder3([{
address: 'muHct3YZ9Nd5Pq7uLYYhXRAxeW4EnpcaLz',
amount: 16
}]);
(function() {b2.merge(b);}).should.throw();
// same signature
// -> this fails: no way to check signatures, since PRIV Keys are not stored
b = getBuilder3([{
address: 'mrPnbY1yKDBsdgbHbS7kJ8GVm8F66hWHLE',
amount: 16
}])
.sign(testdata.dataUnspentSign.keyStrings);
// merge simple
b2 = getBuilder3([{
address: 'mrPnbY1yKDBsdgbHbS7kJ8GVm8F66hWHLE',
amount: 16
}])
.sign(testdata.dataUnspentSign.keyStrings);
(function() {b2.merge(b);}).should.throw();
b2.merge(b, true);
});
it('#merge p2sh/steps', function() {
var b = getP2shBuilder(1); var b = getP2shBuilder(1);
var k1 = testdata.dataUnspentSign.keyStringsP2sh.slice(0,1); var k1 = testdata.dataUnspentSign.keyStringsP2sh.slice(0,1);
var k2 = testdata.dataUnspentSign.keyStringsP2sh.slice(1,2); var k2 = testdata.dataUnspentSign.keyStringsP2sh.slice(1,2);
@ -791,8 +861,5 @@ describe('TransactionBuilder', function() {
b2.signaturesAdded.should.equal(3); b2.signaturesAdded.should.equal(3);
tx = b2.build(); tx = b2.build();
tx.isComplete().should.equal(true); tx.isComplete().should.equal(true);
}); });
}); });