mirror of
https://github.com/aljazceru/btcpayserver.git
synced 2025-12-18 06:24:24 +01:00
fix lq errors and tests (#5371)
* fix lq errors and tests * more fixes * more fixes * fix * fix xmr
This commit is contained in:
@@ -19,7 +19,7 @@ namespace BTCPayServer
|
|||||||
"USDT_X = USDT_BTC * BTC_X",
|
"USDT_X = USDT_BTC * BTC_X",
|
||||||
"USDT_BTC = bitfinex(UST_BTC)",
|
"USDT_BTC = bitfinex(UST_BTC)",
|
||||||
},
|
},
|
||||||
AssetId = new uint256("ce091c998b83c78bb71a632313ba3760f1763d9cfcffae02258ffa9865a37bd2"),
|
AssetId = NetworkType == ChainName.Regtest? null: new uint256("ce091c998b83c78bb71a632313ba3760f1763d9cfcffae02258ffa9865a37bd2"),
|
||||||
DisplayName = "Liquid Tether",
|
DisplayName = "Liquid Tether",
|
||||||
BlockExplorerLink = NetworkType == ChainName.Mainnet ? "https://liquid.network/tx/{0}" : "https://liquid.network/testnet/tx/{0}",
|
BlockExplorerLink = NetworkType == ChainName.Mainnet ? "https://liquid.network/tx/{0}" : "https://liquid.network/testnet/tx/{0}",
|
||||||
NBXplorerNetwork = nbxplorerNetwork,
|
NBXplorerNetwork = nbxplorerNetwork,
|
||||||
@@ -42,7 +42,7 @@ namespace BTCPayServer
|
|||||||
"ETB_BTC = bitpay(ETB_BTC)"
|
"ETB_BTC = bitpay(ETB_BTC)"
|
||||||
},
|
},
|
||||||
Divisibility = 2,
|
Divisibility = 2,
|
||||||
AssetId = new uint256("aa775044c32a7df391902b3659f46dfe004ccb2644ce2ddc7dba31e889391caf"),
|
AssetId = NetworkType == ChainName.Regtest? null: new uint256("aa775044c32a7df391902b3659f46dfe004ccb2644ce2ddc7dba31e889391caf"),
|
||||||
DisplayName = "Ethiopian Birr",
|
DisplayName = "Ethiopian Birr",
|
||||||
BlockExplorerLink = NetworkType == ChainName.Mainnet ? "https://liquid.network/tx/{0}" : "https://liquid.network/testnet/tx/{0}",
|
BlockExplorerLink = NetworkType == ChainName.Mainnet ? "https://liquid.network/tx/{0}" : "https://liquid.network/testnet/tx/{0}",
|
||||||
NBXplorerNetwork = nbxplorerNetwork,
|
NBXplorerNetwork = nbxplorerNetwork,
|
||||||
@@ -65,7 +65,7 @@ namespace BTCPayServer
|
|||||||
"LCAD_BTC = bylls(CAD_BTC)",
|
"LCAD_BTC = bylls(CAD_BTC)",
|
||||||
"CAD_BTC = LCAD_BTC"
|
"CAD_BTC = LCAD_BTC"
|
||||||
},
|
},
|
||||||
AssetId = new uint256("0e99c1a6da379d1f4151fb9df90449d40d0608f6cb33a5bcbfc8c265f42bab0a"),
|
AssetId = NetworkType == ChainName.Regtest? null: new uint256("0e99c1a6da379d1f4151fb9df90449d40d0608f6cb33a5bcbfc8c265f42bab0a"),
|
||||||
DisplayName = "Liquid CAD",
|
DisplayName = "Liquid CAD",
|
||||||
BlockExplorerLink = NetworkType == ChainName.Mainnet ? "https://liquid.network/tx/{0}" : "https://liquid.network/testnet/tx/{0}",
|
BlockExplorerLink = NetworkType == ChainName.Mainnet ? "https://liquid.network/tx/{0}" : "https://liquid.network/testnet/tx/{0}",
|
||||||
NBXplorerNetwork = nbxplorerNetwork,
|
NBXplorerNetwork = nbxplorerNetwork,
|
||||||
|
|||||||
@@ -19,7 +19,8 @@ namespace BTCPayServer
|
|||||||
NewTransactionEvent evtOutputs)
|
NewTransactionEvent evtOutputs)
|
||||||
{
|
{
|
||||||
return evtOutputs.Outputs.Where(output =>
|
return evtOutputs.Outputs.Where(output =>
|
||||||
output.Value is AssetMoney assetMoney && assetMoney.AssetId == AssetId).Select(output =>
|
(output.Value is not AssetMoney && NetworkCryptoCode.Equals(evtOutputs.CryptoCode, StringComparison.InvariantCultureIgnoreCase)) ||
|
||||||
|
(output.Value is AssetMoney assetMoney && assetMoney.AssetId == AssetId)).Select(output =>
|
||||||
{
|
{
|
||||||
var outpoint = new OutPoint(evtOutputs.TransactionData.TransactionHash, output.Index);
|
var outpoint = new OutPoint(evtOutputs.TransactionData.TransactionHash, output.Index);
|
||||||
return (output, outpoint);
|
return (output, outpoint);
|
||||||
|
|||||||
@@ -20,13 +20,13 @@ namespace BTCPayServer.Services.Rates
|
|||||||
}
|
}
|
||||||
public class CurrencyNameTable
|
public class CurrencyNameTable
|
||||||
{
|
{
|
||||||
public static CurrencyNameTable Instance = new CurrencyNameTable();
|
public static CurrencyNameTable Instance = new();
|
||||||
public CurrencyNameTable()
|
public CurrencyNameTable()
|
||||||
{
|
{
|
||||||
_Currencies = LoadCurrency().ToDictionary(k => k.Code);
|
_Currencies = LoadCurrency().ToDictionary(k => k.Code, StringComparer.InvariantCultureIgnoreCase);
|
||||||
}
|
}
|
||||||
|
|
||||||
static readonly Dictionary<string, IFormatProvider> _CurrencyProviders = new Dictionary<string, IFormatProvider>();
|
static readonly Dictionary<string, IFormatProvider> _CurrencyProviders = new();
|
||||||
|
|
||||||
public NumberFormatInfo GetNumberFormatInfo(string currency, bool useFallback)
|
public NumberFormatInfo GetNumberFormatInfo(string currency, bool useFallback)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ namespace BTCPayServer.Rating
|
|||||||
public static CurrencyPair Parse(string str)
|
public static CurrencyPair Parse(string str)
|
||||||
{
|
{
|
||||||
if (!TryParse(str, out var result))
|
if (!TryParse(str, out var result))
|
||||||
throw new FormatException("Invalid currency pair");
|
throw new FormatException($"Invalid currency pair ({str})");
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
public static bool TryParse(string str, out CurrencyPair value)
|
public static bool TryParse(string str, out CurrencyPair value)
|
||||||
|
|||||||
@@ -52,11 +52,12 @@ namespace BTCPayServer.Tests
|
|||||||
{
|
{
|
||||||
tester.ActivateLBTC();
|
tester.ActivateLBTC();
|
||||||
await tester.StartAsync();
|
await tester.StartAsync();
|
||||||
|
|
||||||
|
//https://github.com/ElementsProject/elements/issues/956
|
||||||
|
await tester.LBTCExplorerNode.SendCommandAsync("rescanblockchain");
|
||||||
var user = tester.NewAccount();
|
var user = tester.NewAccount();
|
||||||
user.GrantAccess();
|
await user.GrantAccessAsync();
|
||||||
user.RegisterDerivationScheme("LBTC");
|
|
||||||
user.RegisterDerivationScheme("USDT");
|
|
||||||
user.RegisterDerivationScheme("ETB");
|
|
||||||
await tester.LBTCExplorerNode.GenerateAsync(4);
|
await tester.LBTCExplorerNode.GenerateAsync(4);
|
||||||
//no tether on our regtest, lets create it and set it
|
//no tether on our regtest, lets create it and set it
|
||||||
var tether = tester.NetworkProvider.GetNetwork<ElementsBTCPayNetwork>("USDT");
|
var tether = tester.NetworkProvider.GetNetwork<ElementsBTCPayNetwork>("USDT");
|
||||||
@@ -75,6 +76,10 @@ namespace BTCPayServer.Tests
|
|||||||
.AssetId = etb.AssetId;
|
.AssetId = etb.AssetId;
|
||||||
|
|
||||||
|
|
||||||
|
user.RegisterDerivationScheme("LBTC");
|
||||||
|
user.RegisterDerivationScheme("USDT");
|
||||||
|
user.RegisterDerivationScheme("ETB");
|
||||||
|
|
||||||
//test: register 2 assets on the same elements network and make sure paying an invoice on one does not affect the other in any way
|
//test: register 2 assets on the same elements network and make sure paying an invoice on one does not affect the other in any way
|
||||||
var invoice = await user.BitPay.CreateInvoiceAsync(new Invoice(0.1m, "BTC"));
|
var invoice = await user.BitPay.CreateInvoiceAsync(new Invoice(0.1m, "BTC"));
|
||||||
Assert.Equal(3, invoice.SupportedTransactionCurrencies.Count);
|
Assert.Equal(3, invoice.SupportedTransactionCurrencies.Count);
|
||||||
@@ -82,7 +87,7 @@ namespace BTCPayServer.Tests
|
|||||||
//1 lbtc = 1 btc
|
//1 lbtc = 1 btc
|
||||||
Assert.Equal(1, ci.Rate);
|
Assert.Equal(1, ci.Rate);
|
||||||
var star = await tester.LBTCExplorerNode.SendCommandAsync("sendtoaddress", ci.Address, ci.Due, "", "", false, true,
|
var star = await tester.LBTCExplorerNode.SendCommandAsync("sendtoaddress", ci.Address, ci.Due, "", "", false, true,
|
||||||
1, "UNSET", lbtc.AssetId);
|
1, "UNSET",false, lbtc.AssetId.ToString());
|
||||||
|
|
||||||
TestUtils.Eventually(() =>
|
TestUtils.Eventually(() =>
|
||||||
{
|
{
|
||||||
@@ -95,8 +100,7 @@ namespace BTCPayServer.Tests
|
|||||||
|
|
||||||
ci = invoice.CryptoInfo.Single(info => info.CryptoCode.Equals("USDT"));
|
ci = invoice.CryptoInfo.Single(info => info.CryptoCode.Equals("USDT"));
|
||||||
Assert.Equal(3, invoice.SupportedTransactionCurrencies.Count);
|
Assert.Equal(3, invoice.SupportedTransactionCurrencies.Count);
|
||||||
star = await tester.LBTCExplorerNode.SendCommandAsync("sendtoaddress", ci.Address, ci.Due, "", "", false, true,
|
star = tester.LBTCExplorerNode.SendCommand("sendtoaddress", ci.Address, decimal.Parse(ci.Due), "x", "z", false, true, 1, "unset", false, tether.AssetId.ToString());
|
||||||
1, "UNSET", tether.AssetId);
|
|
||||||
|
|
||||||
TestUtils.Eventually(() =>
|
TestUtils.Eventually(() =>
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -386,11 +386,11 @@ namespace BTCPayServer.Tests
|
|||||||
var newBolt11 = newInvoice.CryptoInfo.First(o => o.PaymentUrls.BOLT11 != null).PaymentUrls.BOLT11;
|
var newBolt11 = newInvoice.CryptoInfo.First(o => o.PaymentUrls.BOLT11 != null).PaymentUrls.BOLT11;
|
||||||
var oldBolt11 = invoice.CryptoInfo.First(o => o.PaymentUrls.BOLT11 != null).PaymentUrls.BOLT11;
|
var oldBolt11 = invoice.CryptoInfo.First(o => o.PaymentUrls.BOLT11 != null).PaymentUrls.BOLT11;
|
||||||
Assert.NotEqual(newBolt11, oldBolt11);
|
Assert.NotEqual(newBolt11, oldBolt11);
|
||||||
Assert.Equal(newInvoice.BtcDue.GetValue(),
|
Assert.Equal(newInvoice.BtcDue.ToDecimal(MoneyUnit.BTC),
|
||||||
BOLT11PaymentRequest.Parse(newBolt11, Network.RegTest).MinimumAmount.ToDecimal(LightMoneyUnit.BTC));
|
BOLT11PaymentRequest.Parse(newBolt11, Network.RegTest).MinimumAmount.ToDecimal(LightMoneyUnit.BTC));
|
||||||
}, 40000);
|
}, 40000);
|
||||||
|
|
||||||
TestLogs.LogInformation($"Paying invoice {newInvoice.Id} remaining due amount {newInvoice.BtcDue.GetValue()} via lightning");
|
TestLogs.LogInformation($"Paying invoice {newInvoice.Id} remaining due amount {newInvoice.BtcDue.GetValue((BTCPayNetwork) tester.DefaultNetwork)} via lightning");
|
||||||
var evt = await tester.WaitForEvent<InvoiceDataChangedEvent>(async () =>
|
var evt = await tester.WaitForEvent<InvoiceDataChangedEvent>(async () =>
|
||||||
{
|
{
|
||||||
await tester.SendLightningPaymentAsync(newInvoice);
|
await tester.SendLightningPaymentAsync(newInvoice);
|
||||||
|
|||||||
@@ -99,7 +99,7 @@ services:
|
|||||||
custom:
|
custom:
|
||||||
|
|
||||||
nbxplorer:
|
nbxplorer:
|
||||||
image: nicolasdorier/nbxplorer:2.3.63
|
image: nicolasdorier/nbxplorer:2.3.66
|
||||||
restart: unless-stopped
|
restart: unless-stopped
|
||||||
ports:
|
ports:
|
||||||
- "32838:32838"
|
- "32838:32838"
|
||||||
@@ -307,7 +307,7 @@ services:
|
|||||||
- "torrcdir:/usr/local/etc/tor"
|
- "torrcdir:/usr/local/etc/tor"
|
||||||
- "tor_servicesdir:/var/lib/tor/hidden_services"
|
- "tor_servicesdir:/var/lib/tor/hidden_services"
|
||||||
monerod:
|
monerod:
|
||||||
image: btcpayserver/monero:0.17.0.0-amd64
|
image: btcpayserver/monero:0.18.2.2-5
|
||||||
restart: unless-stopped
|
restart: unless-stopped
|
||||||
container_name: xmr_monerod
|
container_name: xmr_monerod
|
||||||
entrypoint: sleep 999999
|
entrypoint: sleep 999999
|
||||||
@@ -317,7 +317,7 @@ services:
|
|||||||
ports:
|
ports:
|
||||||
- "18081:18081"
|
- "18081:18081"
|
||||||
monero_wallet:
|
monero_wallet:
|
||||||
image: btcpayserver/monero:0.17.0.0-amd64
|
image: btcpayserver/monero:0.18.2.2-5
|
||||||
restart: unless-stopped
|
restart: unless-stopped
|
||||||
container_name: xmr_wallet_rpc
|
container_name: xmr_wallet_rpc
|
||||||
entrypoint: monero-wallet-rpc --testnet --rpc-bind-ip=0.0.0.0 --disable-rpc-login --confirm-external-bind --rpc-bind-port=18082 --non-interactive --trusted-daemon --daemon-address=monerod:18081 --wallet-file=/wallet/wallet.keys --password-file=/wallet/password --tx-notify="/bin/sh ./scripts/notifier.sh -k -X GET https://host.docker.internal:14142/monerolikedaemoncallback/tx?cryptoCode=xmr&hash=%s"
|
entrypoint: monero-wallet-rpc --testnet --rpc-bind-ip=0.0.0.0 --disable-rpc-login --confirm-external-bind --rpc-bind-port=18082 --non-interactive --trusted-daemon --daemon-address=monerod:18081 --wallet-file=/wallet/wallet.keys --password-file=/wallet/password --tx-notify="/bin/sh ./scripts/notifier.sh -k -X GET https://host.docker.internal:14142/monerolikedaemoncallback/tx?cryptoCode=xmr&hash=%s"
|
||||||
@@ -349,7 +349,7 @@ services:
|
|||||||
elementsd-liquid:
|
elementsd-liquid:
|
||||||
restart: always
|
restart: always
|
||||||
container_name: btcpayserver_elementsd_liquid
|
container_name: btcpayserver_elementsd_liquid
|
||||||
image: btcpayserver/elements:0.21.0.1
|
image: btcpayserver/elements:0.21.0.2-4
|
||||||
environment:
|
environment:
|
||||||
ELEMENTS_CHAIN: elementsregtest
|
ELEMENTS_CHAIN: elementsregtest
|
||||||
ELEMENTS_EXTRA_ARGS: |
|
ELEMENTS_EXTRA_ARGS: |
|
||||||
@@ -364,11 +364,9 @@ services:
|
|||||||
whitelist=0.0.0.0/0
|
whitelist=0.0.0.0/0
|
||||||
rpcallowip=0.0.0.0/0
|
rpcallowip=0.0.0.0/0
|
||||||
validatepegin=0
|
validatepegin=0
|
||||||
initialfreecoins=210000000000000
|
initialfreecoins=2100000000000000
|
||||||
con_dyna_deploy_signal=1
|
con_dyna_deploy_signal=1
|
||||||
con_dyna_deploy_start=0
|
con_dyna_deploy_start=10
|
||||||
con_nminerconfirmationwindow=1
|
|
||||||
con_nrulechangeactivationthreshold=1
|
|
||||||
expose:
|
expose:
|
||||||
- "19332"
|
- "19332"
|
||||||
- "19444"
|
- "19444"
|
||||||
|
|||||||
@@ -96,7 +96,7 @@ services:
|
|||||||
custom:
|
custom:
|
||||||
|
|
||||||
nbxplorer:
|
nbxplorer:
|
||||||
image: nicolasdorier/nbxplorer:2.3.63
|
image: nicolasdorier/nbxplorer:2.3.66
|
||||||
restart: unless-stopped
|
restart: unless-stopped
|
||||||
ports:
|
ports:
|
||||||
- "32838:32838"
|
- "32838:32838"
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
@using BTCPayServer.Services.Wallets
|
@using BTCPayServer.Services.Wallets
|
||||||
|
@using BTCPayServer.Payments
|
||||||
@model BTCPayServer.Components.StoreWalletBalance.StoreWalletBalanceViewModel
|
@model BTCPayServer.Components.StoreWalletBalance.StoreWalletBalanceViewModel
|
||||||
|
@inject BTCPayNetworkProvider NetworkProvider
|
||||||
<div id="StoreWalletBalance-@Model.Store.Id" class="widget store-wallet-balance">
|
<div id="StoreWalletBalance-@Model.Store.Id" class="widget store-wallet-balance">
|
||||||
<div class="d-flex gap-3 align-items-center justify-content-between mb-2">
|
<div class="d-flex gap-3 align-items-center justify-content-between mb-2">
|
||||||
<h6>Wallet Balance</h6>
|
<h6>Wallet Balance</h6>
|
||||||
@@ -38,6 +39,12 @@
|
|||||||
{
|
{
|
||||||
<div class="ct-chart"></div>
|
<div class="ct-chart"></div>
|
||||||
}
|
}
|
||||||
|
else if (!Model.Store.GetSupportedPaymentMethods(NetworkProvider).Any(method => method.PaymentId.PaymentType == BitcoinPaymentType.Instance && method.PaymentId.CryptoCode == Model.CryptoCode))
|
||||||
|
{
|
||||||
|
<p>
|
||||||
|
We would like to show you a chart of your balance but you have not yet <a href="@Url.Action("SetupWallet", "UIStores", new {storeId = Model.Store.Id, cryptoCode = Model.CryptoCode})">configured a wallet</a>.
|
||||||
|
</p>
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
<p>
|
<p>
|
||||||
|
|||||||
@@ -75,7 +75,7 @@ public class StoreWalletBalance : ViewComponent
|
|||||||
if (derivation is not null)
|
if (derivation is not null)
|
||||||
{
|
{
|
||||||
var balance = await wallet.GetBalance(derivation.AccountDerivation, cts.Token);
|
var balance = await wallet.GetBalance(derivation.AccountDerivation, cts.Token);
|
||||||
vm.Balance = balance.Available.GetValue();
|
vm.Balance = balance.Available.GetValue(derivation.Network);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -74,7 +74,7 @@ namespace BTCPayServer.Components.WalletNav
|
|||||||
if (bid is decimal b)
|
if (bid is decimal b)
|
||||||
{
|
{
|
||||||
var currencyData = _currencies.GetCurrencyData(defaultCurrency, true);
|
var currencyData = _currencies.GetCurrencyData(defaultCurrency, true);
|
||||||
vm.BalanceDefaultCurrency = (balance.GetValue() * b).ShowMoney(currencyData.Divisibility);
|
vm.BalanceDefaultCurrency = (balance.GetValue(network) * b).ShowMoney(currencyData.Divisibility);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -383,10 +383,18 @@ namespace BTCPayServer.Controllers
|
|||||||
private async Task SendFreeMoney(Cheater cheater, WalletId walletId, DerivationSchemeSettings paymentMethod)
|
private async Task SendFreeMoney(Cheater cheater, WalletId walletId, DerivationSchemeSettings paymentMethod)
|
||||||
{
|
{
|
||||||
var c = this.ExplorerClientProvider.GetExplorerClient(walletId.CryptoCode);
|
var c = this.ExplorerClientProvider.GetExplorerClient(walletId.CryptoCode);
|
||||||
|
var cashCow = cheater.GetCashCow(walletId.CryptoCode);
|
||||||
|
#if ALTCOINS
|
||||||
|
if (walletId.CryptoCode == "LBTC")
|
||||||
|
{
|
||||||
|
await cashCow.SendCommandAsync("rescanblockchain");
|
||||||
|
}
|
||||||
|
#endif
|
||||||
var addresses = Enumerable.Range(0, 200).Select(_ => c.GetUnusedAsync(paymentMethod.AccountDerivation, DerivationFeature.Deposit, reserve: true)).ToArray();
|
var addresses = Enumerable.Range(0, 200).Select(_ => c.GetUnusedAsync(paymentMethod.AccountDerivation, DerivationFeature.Deposit, reserve: true)).ToArray();
|
||||||
|
|
||||||
await Task.WhenAll(addresses);
|
await Task.WhenAll(addresses);
|
||||||
await cheater.CashCow.GenerateAsync(addresses.Length / 8);
|
await cashCow.GenerateAsync(addresses.Length / 8);
|
||||||
var b = cheater.CashCow.PrepareBatch();
|
var b = cashCow.PrepareBatch();
|
||||||
Random r = new Random();
|
Random r = new Random();
|
||||||
List<Task<uint256>> sending = new List<Task<uint256>>();
|
List<Task<uint256>> sending = new List<Task<uint256>>();
|
||||||
foreach (var a in addresses)
|
foreach (var a in addresses)
|
||||||
@@ -394,7 +402,7 @@ namespace BTCPayServer.Controllers
|
|||||||
sending.Add(b.SendToAddressAsync((await a).Address, Money.Coins(0.1m) + Money.Satoshis(r.Next(0, 90_000_000))));
|
sending.Add(b.SendToAddressAsync((await a).Address, Money.Coins(0.1m) + Money.Satoshis(r.Next(0, 90_000_000))));
|
||||||
}
|
}
|
||||||
await b.SendBatchAsync();
|
await b.SendBatchAsync();
|
||||||
await cheater.CashCow.GenerateAsync(1);
|
await cashCow.GenerateAsync(1);
|
||||||
|
|
||||||
var factory = ServiceProvider.GetRequiredService<NBXplorerConnectionFactory>();
|
var factory = ServiceProvider.GetRequiredService<NBXplorerConnectionFactory>();
|
||||||
|
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ namespace BTCPayServer
|
|||||||
{
|
{
|
||||||
public static class MoneyExtensions
|
public static class MoneyExtensions
|
||||||
{
|
{
|
||||||
public static decimal GetValue(this IMoney m, BTCPayNetwork network = null)
|
public static decimal GetValue(this IMoney m, BTCPayNetwork network)
|
||||||
{
|
{
|
||||||
switch (m)
|
switch (m)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -55,21 +55,26 @@ namespace BTCPayServer.Services.Altcoins.Monero.UI
|
|||||||
[HttpGet()]
|
[HttpGet()]
|
||||||
public async Task<IActionResult> GetStoreMoneroLikePaymentMethods()
|
public async Task<IActionResult> GetStoreMoneroLikePaymentMethods()
|
||||||
{
|
{
|
||||||
var monero = StoreData.GetSupportedPaymentMethods(_BtcPayNetworkProvider)
|
return View(await GetVM(StoreData));
|
||||||
|
}
|
||||||
|
[NonAction]
|
||||||
|
public async Task<MoneroLikePaymentMethodListViewModel> GetVM(StoreData storeData)
|
||||||
|
{
|
||||||
|
var monero = storeData.GetSupportedPaymentMethods(_BtcPayNetworkProvider)
|
||||||
.OfType<MoneroSupportedPaymentMethod>();
|
.OfType<MoneroSupportedPaymentMethod>();
|
||||||
|
|
||||||
var excludeFilters = StoreData.GetStoreBlob().GetExcludedPaymentMethods();
|
var excludeFilters = storeData.GetStoreBlob().GetExcludedPaymentMethods();
|
||||||
|
|
||||||
var accountsList = _MoneroLikeConfiguration.MoneroLikeConfigurationItems.ToDictionary(pair => pair.Key,
|
var accountsList = _MoneroLikeConfiguration.MoneroLikeConfigurationItems.ToDictionary(pair => pair.Key,
|
||||||
pair => GetAccounts(pair.Key));
|
pair => GetAccounts(pair.Key));
|
||||||
|
|
||||||
await Task.WhenAll(accountsList.Values);
|
await Task.WhenAll(accountsList.Values);
|
||||||
return View(new MoneroLikePaymentMethodListViewModel()
|
return new MoneroLikePaymentMethodListViewModel()
|
||||||
{
|
{
|
||||||
Items = _MoneroLikeConfiguration.MoneroLikeConfigurationItems.Select(pair =>
|
Items = _MoneroLikeConfiguration.MoneroLikeConfigurationItems.Select(pair =>
|
||||||
GetMoneroLikePaymentMethodViewModel(monero, pair.Key, excludeFilters,
|
GetMoneroLikePaymentMethodViewModel(monero, pair.Key, excludeFilters,
|
||||||
accountsList[pair.Key].Result))
|
accountsList[pair.Key].Result))
|
||||||
});
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
private Task<GetAccountsResponse> GetAccounts(string cryptoCode)
|
private Task<GetAccountsResponse> GetAccounts(string cryptoCode)
|
||||||
|
|||||||
@@ -1,14 +1,17 @@
|
|||||||
using System;
|
using System;
|
||||||
|
using System.Linq;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using BTCPayServer.Services.Invoices;
|
using BTCPayServer.Services.Invoices;
|
||||||
using Microsoft.Extensions.Hosting;
|
using Microsoft.Extensions.Hosting;
|
||||||
|
using NBitcoin;
|
||||||
using NBitcoin.RPC;
|
using NBitcoin.RPC;
|
||||||
|
|
||||||
namespace BTCPayServer.Services
|
namespace BTCPayServer.Services
|
||||||
{
|
{
|
||||||
public class Cheater : IHostedService
|
public class Cheater : IHostedService
|
||||||
{
|
{
|
||||||
|
private readonly ExplorerClientProvider _prov;
|
||||||
private readonly InvoiceRepository _invoiceRepository;
|
private readonly InvoiceRepository _invoiceRepository;
|
||||||
public RPCClient CashCow { get; set; }
|
public RPCClient CashCow { get; set; }
|
||||||
|
|
||||||
@@ -17,18 +20,47 @@ namespace BTCPayServer.Services
|
|||||||
InvoiceRepository invoiceRepository)
|
InvoiceRepository invoiceRepository)
|
||||||
{
|
{
|
||||||
CashCow = prov.GetExplorerClient("BTC")?.RPCClient;
|
CashCow = prov.GetExplorerClient("BTC")?.RPCClient;
|
||||||
|
_prov = prov;
|
||||||
_invoiceRepository = invoiceRepository;
|
_invoiceRepository = invoiceRepository;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public RPCClient GetCashCow(string cryptoCode)
|
||||||
|
{
|
||||||
|
return _prov.GetExplorerClient(cryptoCode)?.RPCClient;
|
||||||
|
}
|
||||||
|
|
||||||
public async Task UpdateInvoiceExpiry(string invoiceId, TimeSpan seconds)
|
public async Task UpdateInvoiceExpiry(string invoiceId, TimeSpan seconds)
|
||||||
{
|
{
|
||||||
await _invoiceRepository.UpdateInvoiceExpiry(invoiceId, seconds);
|
await _invoiceRepository.UpdateInvoiceExpiry(invoiceId, seconds);
|
||||||
}
|
}
|
||||||
|
|
||||||
Task IHostedService.StartAsync(CancellationToken cancellationToken)
|
async Task IHostedService.StartAsync(CancellationToken cancellationToken)
|
||||||
{
|
{
|
||||||
_ = CashCow?.ScanRPCCapabilitiesAsync(cancellationToken);
|
_ = CashCow?.ScanRPCCapabilitiesAsync(cancellationToken);
|
||||||
return Task.CompletedTask;
|
#if ALTCOINS
|
||||||
|
var liquid = _prov.GetNetwork("LBTC");
|
||||||
|
if (liquid is not null)
|
||||||
|
{
|
||||||
|
var lbtcrpc = GetCashCow(liquid.CryptoCode);
|
||||||
|
await lbtcrpc.SendCommandAsync("rescanblockchain");
|
||||||
|
var elements = _prov.NetworkProviders.GetAll().OfType<ElementsBTCPayNetwork>();
|
||||||
|
foreach (ElementsBTCPayNetwork element in elements)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (element.AssetId is null)
|
||||||
|
{
|
||||||
|
var issueAssetResult = await lbtcrpc.SendCommandAsync("issueasset", 100000, 0);
|
||||||
|
element.AssetId = uint256.Parse(issueAssetResult.Result["asset"].ToString());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
Task IHostedService.StopAsync(CancellationToken cancellationToken)
|
Task IHostedService.StopAsync(CancellationToken cancellationToken)
|
||||||
|
|||||||
@@ -81,7 +81,7 @@ public class OnChainWalletReportProvider : ReportProvider
|
|||||||
var walletId = new WalletId(store.Id, settings.Network.CryptoCode);
|
var walletId = new WalletId(store.Id, settings.Network.CryptoCode);
|
||||||
var command = new CommandDefinition(
|
var command = new CommandDefinition(
|
||||||
commandText:
|
commandText:
|
||||||
"SELECT r.tx_id, r.seen_at, t.blk_id, t.blk_height, r.balance_change " +
|
"SELECT r.tx_id, r.seen_at, t.blk_id, t.blk_height, r.balance_change, r.asset_id " +
|
||||||
"FROM get_wallets_recent(@wallet_id, @code, @interval, NULL, NULL) r " +
|
"FROM get_wallets_recent(@wallet_id, @code, @interval, NULL, NULL) r " +
|
||||||
"JOIN txs t USING (code, tx_id) " +
|
"JOIN txs t USING (code, tx_id) " +
|
||||||
"ORDER BY r.seen_at",
|
"ORDER BY r.seen_at",
|
||||||
@@ -99,6 +99,24 @@ public class OnChainWalletReportProvider : ReportProvider
|
|||||||
var date = (DateTimeOffset)r.seen_at;
|
var date = (DateTimeOffset)r.seen_at;
|
||||||
if (date > queryContext.To)
|
if (date > queryContext.To)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
#if ALTCOINS
|
||||||
|
if (settings.Network is ElementsBTCPayNetwork elementsBTCPayNetwork)
|
||||||
|
{
|
||||||
|
var assetId = (string?)r.asset_id;
|
||||||
|
// if this is an asset scheme, check if the asset id is the same as the network asset id
|
||||||
|
if (elementsBTCPayNetwork.CryptoCode != elementsBTCPayNetwork.NetworkCryptoCode &&
|
||||||
|
assetId is not null && assetId != elementsBTCPayNetwork.AssetId?.ToString())
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
else if (elementsBTCPayNetwork.CryptoCode == elementsBTCPayNetwork.NetworkCryptoCode &&
|
||||||
|
!(assetId is null || assetId == elementsBTCPayNetwork.AssetId?.ToString()))
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
var values = queryContext.AddData();
|
var values = queryContext.AddData();
|
||||||
var balanceChange = Money.Satoshis((long)r.balance_change).ToDecimal(MoneyUnit.BTC);
|
var balanceChange = Money.Satoshis((long)r.balance_change).ToDecimal(MoneyUnit.BTC);
|
||||||
values.Add(date);
|
values.Add(date);
|
||||||
|
|||||||
@@ -158,6 +158,13 @@ public class PaymentsReportProvider : ReportProvider
|
|||||||
{
|
{
|
||||||
cryptoAmount = LightMoney.MilliSatoshis(v).ToDecimal(LightMoneyUnit.BTC);
|
cryptoAmount = LightMoney.MilliSatoshis(v).ToDecimal(LightMoneyUnit.BTC);
|
||||||
}
|
}
|
||||||
|
#if ALTCOINS
|
||||||
|
//assetmoney is an object
|
||||||
|
else if (data.SelectToken("$.value") is JObject valueObject && valueObject.SelectToken("$.value")?.Value<long>() is long amountObj)
|
||||||
|
{
|
||||||
|
cryptoAmount = Money.Satoshis(amountObj).ToDecimal(MoneyUnit.BTC);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
else if (data.SelectToken("$.value")?.Value<long>() is long amount)
|
else if (data.SelectToken("$.value")?.Value<long>() is long amount)
|
||||||
{
|
{
|
||||||
cryptoAmount = Money.Satoshis(amount).ToDecimal(MoneyUnit.BTC);
|
cryptoAmount = Money.Satoshis(amount).ToDecimal(MoneyUnit.BTC);
|
||||||
|
|||||||
@@ -1,22 +1,34 @@
|
|||||||
@using BTCPayServer.Services.Altcoins.Monero.Configuration
|
@using BTCPayServer.Services.Altcoins.Monero.Configuration
|
||||||
@using BTCPayServer.Services.Altcoins.Monero.UI
|
@using BTCPayServer.Services.Altcoins.Monero.UI
|
||||||
@using Microsoft.AspNetCore.Mvc.TagHelpers
|
|
||||||
@using BTCPayServer.Client
|
|
||||||
@using BTCPayServer.Abstractions.TagHelpers
|
|
||||||
@using BTCPayServer.Abstractions.Contracts
|
@using BTCPayServer.Abstractions.Contracts
|
||||||
|
@inject SignInManager<ApplicationUser> SignInManager;
|
||||||
@inject MoneroLikeConfiguration MoneroLikeConfiguration;
|
@inject MoneroLikeConfiguration MoneroLikeConfiguration;
|
||||||
@inject IScopeProvider ScopeProvider
|
@inject IScopeProvider ScopeProvider
|
||||||
|
@inject UIMoneroLikeStoreController UIMoneroLikeStore;
|
||||||
@{
|
@{
|
||||||
var storeId = ScopeProvider.GetCurrentStoreId();
|
var storeId = ScopeProvider.GetCurrentStoreId();
|
||||||
var isActive = !string.IsNullOrEmpty(storeId) && ViewContext.RouteData.Values.TryGetValue("Controller", out var controller) && controller is not null &&
|
|
||||||
nameof(UIMoneroLikeStoreController).StartsWith(controller.ToString() ?? string.Empty, StringComparison.InvariantCultureIgnoreCase);
|
|
||||||
}
|
}
|
||||||
@if (MoneroLikeConfiguration.MoneroLikeConfigurationItems.Any())
|
@if (SignInManager.IsSignedIn(User) && User.IsInRole(Roles.ServerAdmin) && MoneroLikeConfiguration.MoneroLikeConfigurationItems.Any())
|
||||||
{
|
{
|
||||||
<li class="nav-item" permission="@Policies.CanModifyStoreSettings">
|
var store = Context.GetStoreData();
|
||||||
<a asp-action="GetStoreMoneroLikePaymentMethods" asp-controller="UIMoneroLikeStore" asp-route-storeId="@storeId" class="nav-link @(isActive ? "active" : string.Empty)" id="StoreNav-Monero">
|
var result = await UIMoneroLikeStore.GetVM(store);
|
||||||
<span class="me-2 btcpay-status"></span>
|
|
||||||
<span>Monero</span>
|
foreach (var item in result.Items)
|
||||||
</a>
|
{
|
||||||
</li>
|
|
||||||
|
var isActive = !string.IsNullOrEmpty(storeId) && ViewContext.RouteData.Values.TryGetValue("Controller", out var controller) && controller is not null &&
|
||||||
|
nameof(UIMoneroLikeStoreController).StartsWith(controller.ToString() ?? string.Empty, StringComparison.InvariantCultureIgnoreCase) &&
|
||||||
|
ViewContext.RouteData.Values.TryGetValue("cryptoCode", out var cryptoCode) && cryptoCode is not null && cryptoCode.ToString() == item.CryptoCode;
|
||||||
|
<li class="nav-item">
|
||||||
|
<a class="nav-link @(isActive? "active" : "")"
|
||||||
|
asp-route-cryptoCode="@item.CryptoCode"
|
||||||
|
asp-route-storeId="@storeId"
|
||||||
|
asp-action="GetStoreMoneroLikePaymentMethod"
|
||||||
|
asp-controller="UIMoneroLikeStore">
|
||||||
|
<span class="me-2 btcpay-status btcpay-status--@(item.Enabled ? "enabled" : "pending")"></span>
|
||||||
|
<span>@item.CryptoCode Wallet</span>
|
||||||
|
</a>
|
||||||
|
</li>
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,7 +5,7 @@
|
|||||||
@{
|
@{
|
||||||
Layout = "../Shared/_NavLayout.cshtml";
|
Layout = "../Shared/_NavLayout.cshtml";
|
||||||
ViewData["NavPartialName"] = "../UIStores/_Nav";
|
ViewData["NavPartialName"] = "../UIStores/_Nav";
|
||||||
ViewData.SetActivePage(StoreNavPages.OnchainSettings, $"{Model.CryptoCode} Settings");
|
ViewData.SetActivePage(Model.CryptoCode, $"{Model.CryptoCode} Settings", Model.CryptoCode);
|
||||||
}
|
}
|
||||||
|
|
||||||
<div class="row">
|
<div class="row">
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
|
|
||||||
@{
|
@{
|
||||||
Layout = "../Shared/_NavLayout.cshtml";
|
Layout = "../Shared/_NavLayout.cshtml";
|
||||||
ViewData.SetActivePage(StoreNavPages.OnchainSettings, "Monero Settings");
|
ViewData.SetActivePage("Monero Settings", "Monero Settings", "Monero Settings");
|
||||||
ViewData["NavPartialName"] = "../UIStores/_Nav";
|
ViewData["NavPartialName"] = "../UIStores/_Nav";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user