broadcastTx

This commit is contained in:
Matias Alejo Garcia 2015-02-05 17:22:38 -03:00
parent bca18b4292
commit dba306045c
3 changed files with 65 additions and 43 deletions

View File

@ -64,7 +64,7 @@ TxProposal.prototype._updateStatus = function() {
}; };
TxProposal.prototype._getBitcoreTx = function(n) { TxProposal.prototype._getBitcoreTx = function() {
var self = this; var self = this;
var t = new Bitcore.Transaction(); var t = new Bitcore.Transaction();
@ -80,6 +80,13 @@ TxProposal.prototype._getBitcoreTx = function(n) {
}; };
TxProposal.prototype.getRawTx = function() {
var t = this._getBitcoreTx();
return t.serialize();
};
TxProposal.prototype.addAction = function(copayerId, type, signatures) { TxProposal.prototype.addAction = function(copayerId, type, signatures) {
var action = new TxProposalAction({ var action = new TxProposalAction({
copayerId: copayerId, copayerId: copayerId,

View File

@ -96,6 +96,10 @@ Wallet.prototype.getCopayer = function(copayerId) {
}; };
Wallet.prototype.getNetworkName = function() {
return this.isTestnet ? 'testnet' : 'livenet';
};
Wallet.prototype._getBitcoreNetwork = function() { Wallet.prototype._getBitcoreNetwork = function() {
return this.isTestnet ? Bitcore.Networks.testnet : Bitcore.Networks.livenet; return this.isTestnet ? Bitcore.Networks.testnet : Bitcore.Networks.livenet;
}; };

View File

@ -263,52 +263,62 @@ CopayServer.prototype._getBlockExplorer = function(provider, network) {
} }
}; };
/**
* _getUtxos
*
* @param opts.walletId
*/
CopayServer.prototype._getUtxos = function(opts, cb) { CopayServer.prototype._getUtxos = function(opts, cb) {
var self = this; var self = this;
// Get addresses for this wallet
self.storage.fetchAddresses(opts.walletId, function(err, addresses) { self.storage.fetchWallet(opts.walletId, function(err, wallet) {
if (err) return cb(err); if (err) return cb(err);
if (addresses.length == 0) return cb(new ClientError('The wallet has no addresses'));
var addressStrs = _.pluck(addresses, 'address'); // Get addresses for this wallet
var addressToPath = _.indexBy(addresses, 'address'); // TODO : check performance self.storage.fetchAddresses(opts.walletId, function(err, addresses) {
var bc = self._getBlockExplorer('insight', opts.network);
bc.getUnspentUtxos(addressStrs, function(err, utxos) {
if (err) return cb(err); if (err) return cb(err);
if (addresses.length == 0) return cb(new ClientError('The wallet has no addresses'));
self.getPendingTxs({ var addressStrs = _.pluck(addresses, 'address');
walletId: opts.walletId var addressToPath = _.indexBy(addresses, 'address'); // TODO : check performance
}, function(err, txps) {
var bc = self._getBlockExplorer('insight', wallet.getNetworkName());
bc.getUnspentUtxos(addressStrs, function(err, utxos) {
if (err) return cb(err); if (err) return cb(err);
var inputs = _.chain(txps) self.getPendingTxs({
.pluck('inputs') walletId: opts.walletId
.flatten() }, function(err, txps) {
.map(function(utxo) { if (err) return cb(err);
return utxo.txid + '|' + utxo.vout
})
.value();
var dictionary = _.reduce(utxos, function(memo, utxo) { var inputs = _.chain(txps)
memo[utxo.txid + '|' + utxo.vout] = utxo; .pluck('inputs')
return memo; .flatten()
}, {}); .map(function(utxo) {
return utxo.txid + '|' + utxo.vout
})
.value();
_.each(inputs, function(input) { var dictionary = _.reduce(utxos, function(memo, utxo) {
if (dictionary[input]) { memo[utxo.txid + '|' + utxo.vout] = utxo;
dictionary[input].locked = true; return memo;
} }, {});
_.each(inputs, function(input) {
if (dictionary[input]) {
dictionary[input].locked = true;
}
});
// Needed for the clients to sign UTXOs
_.each(utxos, function(utxo) {
utxo.path = addressToPath[utxo.address].path;
utxo.publicKeys = addressToPath[utxo.address].publicKeys;
});
return cb(null, utxos);
}); });
// Needed for the clients to sign UTXOs
_.each(utxos, function(utxo) {
utxo.path = addressToPath[utxo.address].path;
utxo.publicKeys = addressToPath[utxo.address].publicKeys;
});
return cb(null, utxos);
}); });
}); });
}); });
@ -452,11 +462,12 @@ CopayServer.prototype.getTx = function(opts, cb) {
}); });
}; };
CopayServer.prototype._broadcastTx = function(rawTx, cb) { CopayServer.prototype._broadcastTx = function(txp, networkName, cb) {
// TODO: this should attempt to broadcast _all_ accepted and not-yet broadcasted (status=='accepted') txps? var raw = txp.getRawTx();
cb = cb || function() {}; var bc = self._getBlockExplorer('insight', networkName);
bc.broadcast(raw, function(err, txid) {
throw 'not implemented'; return cb(err, txid);
})
}; };
/** /**
@ -486,9 +497,9 @@ CopayServer.prototype.signTx = function(opts, cb) {
var action = _.find(txp.actions, { var action = _.find(txp.actions, {
copayerId: opts.copayerId copayerId: opts.copayerId
}); });
if (action) if (action)
return cb(new ClientError('CVOTED', 'Copayer already voted on this transaction proposal')); return cb(new ClientError('CVOTED', 'Copayer already voted on this transaction proposal'));
if (txp.status != 'pending') if (txp.status != 'pending')
return cb(new ClientError('TXNOTPENDING', 'The transaction proposal is not pending')); return cb(new ClientError('TXNOTPENDING', 'The transaction proposal is not pending'));
var copayer = wallet.getCopayer(opts.copayerId); var copayer = wallet.getCopayer(opts.copayerId);
@ -502,7 +513,7 @@ CopayServer.prototype.signTx = function(opts, cb) {
if (err) return cb(err); if (err) return cb(err);
if (txp.status == 'accepted') { if (txp.status == 'accepted') {
self._broadcastTx(txp.rawTx, function(err, txid) { self._broadcastTx(txp, wallet.getNetworkName(), function(err, txid) {
if (err) return cb(err); if (err) return cb(err);
tx.setBroadcasted(txid); tx.setBroadcasted(txid);