/// <summary>
        /// Buy the NFT based on the NFT and Neblio Address
        /// </summary>
        /// <param name="neblioAddress"></param>
        /// <param name="receiver"></param>
        /// <param name="nft"></param>
        /// <returns></returns>
        public async Task <(bool, string)> BuyNFT(string neblioAddress, string receiver, INFT nft)
        {
            if (!nft.PriceActive)
            {
                return(false, "NFT does not have setted up the price. It is not sellable NFT.");
            }

            if (IsLocked())
            {
                await InvokeAccountLockedEvent();

                return(false, "Account is locked.");
            }

            var res = await CheckSpendableDoge(nft.Price);

            if (res.Item2 == null)
            {
                await InvokeErrorDuringSendEvent(res.Item1, "Not enough spendable inputs");

                return(false, res.Item1);
            }

            var nftid = nft.Utxo + ":" + nft.UtxoIndex.ToString();
            var msg   = neblioAddress + "=" + String.Format("{0:X}", nftid.GetHashCode());

            // fill input data for sending tx
            var dto = new SendTxData() // please check SendTxData for another properties such as specify source UTXOs
            {
                Amount          = nft.Price,
                SenderAddress   = Address,
                ReceiverAddress = receiver,
                CustomMessage   = msg
            };

            try
            {
                // send tx
                var transaction = DogeTransactionHelpers.GetDogeTransactionWithMessageAsync(dto, BAddress, res.Item2);

                var result = await SignBroadcastAndInvokeSucessEvent(transaction, Secret, res.Item2, "Doge Payment Sent");

                if (result.Item1)
                {
                    return(true, result.Item2);
                }
            }
            catch (Exception ex)
            {
                await InvokeErrorDuringSendEvent(ex.Message, "Unknown Error");

                return(false, ex.Message);
            }

            await InvokeErrorDuringSendEvent("Unknown Error", "Unknown Error");

            return(false, "Unexpected error during send.");
        }
Пример #2
0
 /// <summary>
 /// Function will send standard Neblio transaction with included message.
 /// </summary>
 /// <param name="data">Send data, please see SendTxData class for the details - this include field for custom message</param>
 /// <param name="ekey">Input EncryptionKey of the account</param>
 /// <param name="utxos">Optional input neblio utxo</param>
 /// <returns>New Transaction Hash - TxId</returns>
 public static Transaction GetDogeTransactionWithMessageAsync(SendTxData data, BitcoinAddress addressForTx, ICollection <Utxo> utxos)
 {
     return(GetTransactionObject(data, addressForTx, utxos, withMessage: true));
 }
        /// <summary>
        /// Send Doge payment with multiple inputs
        /// </summary>
        /// <param name="receiver">Receiver Doge Address</param>
        /// <param name="amount">Ammount in Doge</param>
        /// <param name="utxos"></param>
        /// <param name="message"></param>
        /// <param name="fee"></param>
        /// <returns></returns>
        public async Task <(bool, string)> SendMultipleInputPayment(string receiver, double amount, List <Utxo> utxos, string message = "", UInt64 fee = 100000000)
        {
            if (IsLocked())
            {
                await InvokeAccountLockedEvent();

                return(false, "Account is locked.");
            }
            var res = await CheckSpendableDoge(amount + 5);

            if (res.Item2 == null)
            {
                await InvokeErrorDuringSendEvent(res.Item1, "Not enough spendable inputs");

                return(false, res.Item1);
            }

            if (utxos.Count > 0)
            {
                res.Item2 = utxos;
            }

            // fill input data for sending tx
            var dto = new SendTxData() // please check SendTxData for another properties such as specify source UTXOs
            {
                Amount          = amount,
                SenderAddress   = Address,
                ReceiverAddress = receiver,
                CustomMessage   = message
            };

            try
            {
                // send tx
                var         rtxid = string.Empty;
                Transaction transaction;
                if (string.IsNullOrEmpty(message))
                {
                    transaction = DogeTransactionHelpers.GetDogeTransactionAsync(dto, BAddress, res.Item2);
                }
                else
                {
                    transaction = DogeTransactionHelpers.GetDogeTransactionWithMessageAsync(dto, BAddress, res.Item2);
                }

                var result = await SignBroadcastAndInvokeSucessEvent(transaction, Secret, res.Item2, "Doge Payment Sent");

                if (result.Item1)
                {
                    return(true, result.Item2);
                }
            }
            catch (Exception ex)
            {
                await InvokeErrorDuringSendEvent(ex.Message, "Unknown Error");

                return(false, ex.Message);
            }

            await InvokeErrorDuringSendEvent("Unknown Error", "Unknown Error");

            return(false, "Unexpected error during send.");
        }
Пример #4
0
        private static Transaction GetTransactionObject(SendTxData data, BitcoinAddress addressForTx, ICollection <Utxo> utxos, bool withMessage = false)
        {
            if (data == null)
            {
                throw new Exception("Data cannot be null!");
            }

            if (addressForTx == null)
            {
                throw new Exception("BitcoinAddress object cannot be null!");
            }

            // create receiver address
            BitcoinAddress recaddr;

            try
            {
                recaddr = BitcoinAddress.Create(data.ReceiverAddress, Network);
            }
            catch (Exception)
            {
                throw new Exception("Cannot send transaction. cannot create receiver address!");
            }

            // create template for new tx from last one
            var tx = GetTransactionWithDogecoinInputs(utxos, addressForTx);

            if (tx.Item1 == null)
            {
                throw new Exception("Cannot create the transaction object.");
            }

            var transaction   = tx.Item1;
            var allDogelCoins = tx.Item2;

            try
            {
                var fee = CalcFee(transaction.Inputs.Count, 1, data.CustomMessage, false);

                if (allDogelCoins < (data.Amount))
                {
                    throw new Exception("Not enough Doge to spend.");
                }

                var amountinSat = Convert.ToUInt64(data.Amount * FromSatToMainRatio);
                var diffinSat   = (Convert.ToUInt64(allDogelCoins) * FromSatToMainRatio) - amountinSat - Convert.ToUInt64(fee);

                // create outputs
                transaction.Outputs.Add(new Money(amountinSat), recaddr.ScriptPubKey); // send to receiver required amount

                if (withMessage)
                {
                    var bytes = Encoding.UTF8.GetBytes(data.CustomMessage);
                    transaction.Outputs.Add(new TxOut()
                    {
                        Value        = (long)0,
                        ScriptPubKey = TxNullDataTemplate.Instance.GenerateScriptPubKey(bytes)
                    });
                }

                if (diffinSat > 0)
                {
                    transaction.Outputs.Add(new Money(Convert.ToUInt64(diffinSat)), addressForTx.ScriptPubKey); // get diff back to sender address
                }
            }
            catch (Exception ex)
            {
                throw new Exception("Exception during creating outputs. " + ex.Message);
            }

            return(transaction);
        }