public async Task <Transaction> GetTransaction(string id)
        {
            var tx = await _client.GetRawTransactionAsync(id);

            if (tx == null)
            {
                return(null);
            }
            var transaction = new Transaction
            {
                Blockhash       = tx.Blockhash,
                TransactionId   = tx.Txid,
                Size            = tx.Size,
                TransactionIn   = new List <In>(),
                TransactionsOut = new List <Out>(),
            };

            // this fails b/c no input validation
            // Debug.Assert(id == transaction.TransactionId);

            int index = 0;

            foreach (var rpcIn in tx.Vin)
            {
                var inp = new In {
                    Index = index
                };

                if (rpcIn.Coinbase == null)
                {
                    string hexScript                 = rpcIn.ScriptSig.Hex;
                    byte[] decodedScript             = Encoders.Hex.DecodeData(hexScript);
                    Script script                    = new Script(decodedScript);
                    PayToPubkeyHashTemplate template = new PayToPubkeyHashTemplate();


                    PayToPubkeyHashScriptSigParameters param = template.ExtractScriptSigParameters(script);
                    if (param != null)
                    {
                        PubKey pubKey = param.PublicKey;
                        BitcoinPubKeyAddress address = pubKey.GetAddress(NetworkSpec.ObsidianMain());

                        inp.Address = address.ToString();
                    }
                    else
                    {
                        inp.Address = "none";
                    }

                    inp.TransactionId = rpcIn.Txid;
                    inp.VOut          = (int)rpcIn.Vout;
                    inp.Sequence      = rpcIn.Sequence;
                    inp.ScriptSigHex  = rpcIn.ScriptSig.Hex;
                }
                else
                {
                    inp.Coinbase = rpcIn.Coinbase;
                    inp.Sequence = rpcIn.Sequence;
                }

                transaction.TransactionIn.Add(inp);
            }

            if (transaction.TransactionIn[0].Coinbase != null)
            {
                //Debug.Assert(transaction.TransactionIn.Count == 1);
                transaction.IsCoinBase = true;
            }

            index = 0;
            foreach (var output in tx.Vout)
            {
                var @out = new Out
                {
                    TransactionId = transaction.TransactionId,
                    Value         = output.Value,
                    Quantity      = output.N,
                    AssetId       = null,
                    Index         = index++
                };
                if (output.ScriptPubKey.Addresses != null)                 // Satoshi 14.2
                {
                    @out.Address = output.ScriptPubKey.Addresses.FirstOrDefault();
                }
                else
                {
                    string hexScript = output.ScriptPubKey.Hex;

                    if (!string.IsNullOrEmpty(hexScript))
                    {
                        byte[] decodedScript         = Encoders.Hex.DecodeData(hexScript);
                        Script script                = new Script(decodedScript);
                        var    pubKey                = PayToPubkeyTemplate.Instance.ExtractScriptPubKeyParameters(script);
                        BitcoinPubKeyAddress address = pubKey.GetAddress(NetworkSpec.ObsidianMain());
                        @out.Address = address.ToString();
                    }
                    else
                    {
                        @out.Address = "none";
                    }
                }

                transaction.TransactionsOut.Add(@out);
            }



            return(transaction);
        }
示例#2
0
        public async Task <Transaction> GetTransaction(string id)
        {
            try
            {
                GetRawTransactionRpcModel tx = await RpcClient.GetRawTransactionAsync(id);

                if (tx == null)
                {
                    return(null);
                }

                TransactionType transactiontype = GetTransactionType(tx);

                var transaction = new Transaction
                {
                    OriginalJson    = tx.OriginalJson,
                    TransactionType = transactiontype,
                    Blockhash       = tx.Blockhash,
                    TransactionId   = tx.Txid,
                    Size            = tx.Size,
                    TransactionIn   = new List <VIn>(),
                    TransactionsOut = new List <Out>(),
                    Time            = tx.GetTime()
                };


                int index = 0;
                foreach (var rpcIn in tx.Vin)
                {
                    var vIn = new VIn
                    {
                        Index        = index,
                        Coinbase     = rpcIn.Coinbase,
                        Sequence     = rpcIn.Sequence,
                        ScriptSigHex = rpcIn.ScriptSig?.Hex,
                        AssetId      = null,
                        // pointer to previous tx/vout:
                        PrevTxIdPointer = rpcIn.Txid,
                        PrevVOutPointer = (int)rpcIn.Vout,
                        // we'll try to fetch this id possible
                        PrevVOutFetchedAddress = null,
                        PrevVOutFetchedValue   = 0
                    };

                    if (rpcIn.Txid != null)
                    {
                        // Retrieve the origin address by retrieving the previous transaction and extracting the receive address and value
                        var previousTx = await RpcClient.GetRawTransactionAsync(rpcIn.Txid);

                        if (previousTx != null)
                        {
                            var n = rpcIn.Vout;
                            Debug.Assert(n == previousTx.Vout[n].N);
                            vIn.PrevVOutFetchedAddress = previousTx.Vout[n].ScriptPubKey.Addresses.First();
                            vIn.PrevVOutFetchedValue   = previousTx.Vout[n].Value;
                        }
                    }
                    transaction.TransactionIn.Add(vIn);
                }



                index = 0;
                foreach (var output in tx.Vout)
                {
                    var @out = new Out
                    {
                        TransactionId = transaction.TransactionId,
                        Value         = output.Value,
                        Quantity      = output.N,
                        AssetId       = null,
                        Index         = index++,
                    };

                    if (output.ScriptPubKey.Addresses != null)                     // Satoshi 14.2
                    {
                        @out.Address = output.ScriptPubKey.Addresses.FirstOrDefault();
                    }
                    else
                    {
                        string hexScript = output.ScriptPubKey.Hex;

                        if (!string.IsNullOrEmpty(hexScript))
                        {
                            byte[] decodedScript = Encoders.Hex.DecodeData(hexScript);
                            Script script        = new Script(decodedScript);
                            var    pubKey        = PayToPubkeyTemplate.Instance.ExtractScriptPubKeyParameters(script);
                            if (pubKey != null)
                            {
                                BitcoinPubKeyAddress address = pubKey.GetAddress(NetworkSpec.ObsidianMain());
                                @out.Address = address.ToString();
                            }
                            else
                            {
                                @out.Address = script.ToString();
                            }
                        }
                        else
                        {
                            Debug.Assert(output.ScriptPubKey.Type == NonStandardAddress);
                            @out.Address = output.ScriptPubKey.Type;
                        }
                    }
                    transaction.TransactionsOut.Add(@out);
                }

                return(transaction);
            }
            catch { }
            return(null);
        }