Btcpay abstract BTCPayNetwork -- Alternative PR to #865 (#868)

* BitcoinSpecificBtcPayNetwork - abstract BTCPayNetwork

* some type fixes

* fix tests

* simplify fetching handler in invoice controller

* rename network base and bitcoin classes

* abstract serializer to network level

* fix serializer when network not provided

* fix serializer when network not provided

* fix serializer when network not provided

* try fixes for isolating pull request
This commit is contained in:
Andrew Camilleri
2019-05-29 09:43:50 +00:00
committed by Nicolas Dorier
parent 90852fe951
commit d3e3c31b0c
39 changed files with 223 additions and 167 deletions

View File

@@ -5,6 +5,7 @@ using System.Linq;
using System.Threading.Tasks; using System.Threading.Tasks;
using NBitcoin; using NBitcoin;
using NBXplorer; using NBXplorer;
using Newtonsoft.Json;
namespace BTCPayServer namespace BTCPayServer
{ {
@@ -42,37 +43,17 @@ namespace BTCPayServer
public string DefaultConfigurationFile { get; set; } public string DefaultConfigurationFile { get; set; }
public int DefaultPort { get; set; } public int DefaultPort { get; set; }
} }
public class BTCPayNetwork
public class BTCPayNetwork:BTCPayNetworkBase
{ {
public Network NBitcoinNetwork { get; set; } public Network NBitcoinNetwork { get; set; }
public string CryptoCode { get; internal set; }
public string BlockExplorerLink { get; internal set; }
public string UriScheme { get; internal set; }
public string DisplayName { get; set; }
[Obsolete("Should not be needed")]
public bool IsBTC
{
get
{
return CryptoCode == "BTC";
}
}
public string CryptoImagePath { get; set; }
public string LightningImagePath { get; set; }
public NBXplorer.NBXplorerNetwork NBXplorerNetwork { get; set; } public NBXplorer.NBXplorerNetwork NBXplorerNetwork { get; set; }
public bool SupportRBF { get; internal set; }
public string LightningImagePath { get; set; }
public BTCPayDefaultSettings DefaultSettings { get; set; } public BTCPayDefaultSettings DefaultSettings { get; set; }
public KeyPath CoinType { get; internal set; } public KeyPath CoinType { get; internal set; }
public int MaxTrackedConfirmation { get; internal set; } = 6;
public string[] DefaultRateRules { get; internal set; } = Array.Empty<string>();
public bool SupportRBF { get; internal set; }
public Dictionary<uint, DerivationType> ElectrumMapping = new Dictionary<uint, DerivationType>(); public Dictionary<uint, DerivationType> ElectrumMapping = new Dictionary<uint, DerivationType>();
public override string ToString()
{
return CryptoCode;
}
public KeyPath GetRootKeyPath(DerivationType type) public KeyPath GetRootKeyPath(DerivationType type)
{ {
@@ -107,5 +88,52 @@ namespace BTCPayServer
return new KeyPath(NBitcoinNetwork.Consensus.SupportSegwit ? "49'" : "44'") return new KeyPath(NBitcoinNetwork.Consensus.SupportSegwit ? "49'" : "44'")
.Derive(CoinType); .Derive(CoinType);
} }
public override T ToObject<T>(string json)
{
return NBXplorerNetwork.Serializer.ToObject<T>(json);
}
public override string ToString<T>(T obj)
{
return NBXplorerNetwork.Serializer.ToString(obj);
}
}
public abstract class BTCPayNetworkBase
{
public string CryptoCode { get; internal set; }
public string BlockExplorerLink { get; internal set; }
public string UriScheme { get; internal set; }
public string DisplayName { get; set; }
[Obsolete("Should not be needed")]
public bool IsBTC
{
get
{
return CryptoCode == "BTC";
}
}
public string CryptoImagePath { get; set; }
public int MaxTrackedConfirmation { get; internal set; } = 6;
public string[] DefaultRateRules { get; internal set; } = Array.Empty<string>();
public override string ToString()
{
return CryptoCode;
}
public virtual T ToObject<T>(string json)
{
return JsonConvert.DeserializeObject<T>(json);
}
public virtual string ToString<T>(T obj)
{
return JsonConvert.SerializeObject(obj);
}
} }
} }

View File

@@ -10,7 +10,7 @@ namespace BTCPayServer
{ {
public partial class BTCPayNetworkProvider public partial class BTCPayNetworkProvider
{ {
Dictionary<string, BTCPayNetwork> _Networks = new Dictionary<string, BTCPayNetwork>(); Dictionary<string, BTCPayNetworkBase> _Networks = new Dictionary<string, BTCPayNetworkBase>();
private readonly NBXplorerNetworkProvider _NBXplorerNetworkProvider; private readonly NBXplorerNetworkProvider _NBXplorerNetworkProvider;
@@ -26,7 +26,7 @@ namespace BTCPayServer
{ {
NetworkType = filtered.NetworkType; NetworkType = filtered.NetworkType;
_NBXplorerNetworkProvider = new NBXplorerNetworkProvider(filtered.NetworkType); _NBXplorerNetworkProvider = new NBXplorerNetworkProvider(filtered.NetworkType);
_Networks = new Dictionary<string, BTCPayNetwork>(); _Networks = new Dictionary<string, BTCPayNetworkBase>();
cryptoCodes = cryptoCodes.Select(c => c.ToUpperInvariant()).ToArray(); cryptoCodes = cryptoCodes.Select(c => c.ToUpperInvariant()).ToArray();
foreach (var network in filtered._Networks) foreach (var network in filtered._Networks)
{ {
@@ -54,15 +54,15 @@ namespace BTCPayServer
InitViacoin(); InitViacoin();
// Assume that electrum mappings are same as BTC if not specified // Assume that electrum mappings are same as BTC if not specified
foreach (var network in _Networks) foreach (var network in _Networks.Values.OfType<BTCPayNetwork>())
{ {
if(network.Value.ElectrumMapping.Count == 0) if(network.ElectrumMapping.Count == 0)
{ {
network.Value.ElectrumMapping = GetNetwork("BTC").ElectrumMapping; network.ElectrumMapping = GetNetwork<BTCPayNetwork>("BTC").ElectrumMapping;
if (!network.Value.NBitcoinNetwork.Consensus.SupportSegwit) if (!network.NBitcoinNetwork.Consensus.SupportSegwit)
{ {
network.Value.ElectrumMapping = network.ElectrumMapping =
network.Value.ElectrumMapping network.ElectrumMapping
.Where(kv => kv.Value == DerivationType.Legacy) .Where(kv => kv.Value == DerivationType.Legacy)
.ToDictionary(k => k.Key, k => k.Value); .ToDictionary(k => k.Key, k => k.Value);
} }
@@ -86,14 +86,14 @@ namespace BTCPayServer
} }
[Obsolete("To use only for legacy stuff")] [Obsolete("To use only for legacy stuff")]
public BTCPayNetwork BTC => GetNetwork("BTC"); public BTCPayNetwork BTC => GetNetwork<BTCPayNetwork>("BTC");
public void Add(BTCPayNetwork network) public void Add(BTCPayNetworkBase network)
{ {
_Networks.Add(network.CryptoCode.ToUpperInvariant(), network); _Networks.Add(network.CryptoCode.ToUpperInvariant(), network);
} }
public IEnumerable<BTCPayNetwork> GetAll() public IEnumerable<BTCPayNetworkBase> GetAll()
{ {
return _Networks.Values.ToArray(); return _Networks.Values.ToArray();
} }
@@ -103,14 +103,14 @@ namespace BTCPayServer
return _Networks.ContainsKey(cryptoCode.ToUpperInvariant()); return _Networks.ContainsKey(cryptoCode.ToUpperInvariant());
} }
public BTCPayNetwork GetNetwork(string cryptoCode) public T GetNetwork<T>(string cryptoCode) where T: BTCPayNetworkBase
{ {
if(!_Networks.TryGetValue(cryptoCode.ToUpperInvariant(), out BTCPayNetwork network)) if(!_Networks.TryGetValue(cryptoCode.ToUpperInvariant(), out BTCPayNetworkBase network))
{ {
if (cryptoCode == "XBT") if (cryptoCode == "XBT")
return GetNetwork("BTC"); return GetNetwork<T>("BTC");
} }
return network; return network as T;
} }
} }
} }

View File

@@ -53,7 +53,7 @@ namespace BTCPayServer.Rating
for (int i = 3; i < 5; i++) for (int i = 3; i < 5; i++)
{ {
var potentialCryptoName = currencyPair.Substring(0, i); var potentialCryptoName = currencyPair.Substring(0, i);
var network = _NetworkProvider.GetNetwork(potentialCryptoName); var network = _NetworkProvider.GetNetwork<BTCPayNetworkBase>(potentialCryptoName);
if (network != null) if (network != null)
{ {
value = new CurrencyPair(network.CryptoCode, currencyPair.Substring(i)); value = new CurrencyPair(network.CryptoCode, currencyPair.Substring(i));

View File

@@ -44,14 +44,14 @@ namespace BTCPayServer.Tests
Directory.CreateDirectory(_Directory); Directory.CreateDirectory(_Directory);
NetworkProvider = new BTCPayNetworkProvider(NetworkType.Regtest); NetworkProvider = new BTCPayNetworkProvider(NetworkType.Regtest);
ExplorerNode = new RPCClient(RPCCredentialString.Parse(GetEnvironment("TESTS_BTCRPCCONNECTION", "server=http://127.0.0.1:43782;ceiwHEbqWI83:DwubwWsoo3")), NetworkProvider.GetNetwork("BTC").NBitcoinNetwork); ExplorerNode = new RPCClient(RPCCredentialString.Parse(GetEnvironment("TESTS_BTCRPCCONNECTION", "server=http://127.0.0.1:43782;ceiwHEbqWI83:DwubwWsoo3")), NetworkProvider.GetNetwork<BTCPayNetwork>("BTC").NBitcoinNetwork);
ExplorerNode.ScanRPCCapabilities(); ExplorerNode.ScanRPCCapabilities();
LTCExplorerNode = new RPCClient(RPCCredentialString.Parse(GetEnvironment("TESTS_LTCRPCCONNECTION", "server=http://127.0.0.1:43783;ceiwHEbqWI83:DwubwWsoo3")), NetworkProvider.GetNetwork("LTC").NBitcoinNetwork); LTCExplorerNode = new RPCClient(RPCCredentialString.Parse(GetEnvironment("TESTS_LTCRPCCONNECTION", "server=http://127.0.0.1:43783;ceiwHEbqWI83:DwubwWsoo3")), NetworkProvider.GetNetwork<BTCPayNetwork>("LTC").NBitcoinNetwork);
ExplorerClient = new ExplorerClient(NetworkProvider.GetNetwork("BTC").NBXplorerNetwork, new Uri(GetEnvironment("TESTS_BTCNBXPLORERURL", "http://127.0.0.1:32838/"))); ExplorerClient = new ExplorerClient(NetworkProvider.GetNetwork<BTCPayNetwork>("BTC").NBXplorerNetwork, new Uri(GetEnvironment("TESTS_BTCNBXPLORERURL", "http://127.0.0.1:32838/")));
LTCExplorerClient = new ExplorerClient(NetworkProvider.GetNetwork("LTC").NBXplorerNetwork, new Uri(GetEnvironment("TESTS_LTCNBXPLORERURL", "http://127.0.0.1:32838/"))); LTCExplorerClient = new ExplorerClient(NetworkProvider.GetNetwork<BTCPayNetwork>("LTC").NBXplorerNetwork, new Uri(GetEnvironment("TESTS_LTCNBXPLORERURL", "http://127.0.0.1:32838/")));
var btc = NetworkProvider.GetNetwork("BTC").NBitcoinNetwork; var btc = NetworkProvider.GetNetwork<BTCPayNetwork>("BTC").NBitcoinNetwork;
CustomerLightningD = LightningClientFactory.CreateClient(GetEnvironment("TEST_CUSTOMERLIGHTNINGD", "type=clightning;server=tcp://127.0.0.1:30992/"), btc); CustomerLightningD = LightningClientFactory.CreateClient(GetEnvironment("TEST_CUSTOMERLIGHTNINGD", "type=clightning;server=tcp://127.0.0.1:30992/"), btc);
MerchantLightningD = LightningClientFactory.CreateClient(GetEnvironment("TEST_MERCHANTLIGHTNINGD", "type=clightning;server=tcp://127.0.0.1:30993/"), btc); MerchantLightningD = LightningClientFactory.CreateClient(GetEnvironment("TEST_MERCHANTLIGHTNINGD", "type=clightning;server=tcp://127.0.0.1:30993/"), btc);

View File

@@ -95,7 +95,7 @@ namespace BTCPayServer.Tests
} }
public async Task<WalletId> RegisterDerivationSchemeAsync(string cryptoCode, bool segwit = false) public async Task<WalletId> RegisterDerivationSchemeAsync(string cryptoCode, bool segwit = false)
{ {
SupportedNetwork = parent.NetworkProvider.GetNetwork(cryptoCode); SupportedNetwork = parent.NetworkProvider.GetNetwork<BTCPayNetwork>(cryptoCode);
var store = parent.PayTester.GetController<StoresController>(UserId, StoreId); var store = parent.PayTester.GetController<StoresController>(UserId, StoreId);
ExtKey = new ExtKey().GetWif(SupportedNetwork.NBitcoinNetwork); ExtKey = new ExtKey().GetWif(SupportedNetwork.NBitcoinNetwork);
DerivationScheme = new DerivationStrategyFactory(SupportedNetwork.NBitcoinNetwork).Parse(ExtKey.Neuter().ToString() + (segwit ? "" : "-[legacy]")); DerivationScheme = new DerivationStrategyFactory(SupportedNetwork.NBitcoinNetwork).Parse(ExtKey.Neuter().ToString() + (segwit ? "" : "-[legacy]"));

View File

@@ -1499,8 +1499,8 @@ namespace BTCPayServer.Tests
var testnetNetworkProvider = new BTCPayNetworkProvider(NetworkType.Testnet); var testnetNetworkProvider = new BTCPayNetworkProvider(NetworkType.Testnet);
var regtestNetworkProvider = new BTCPayNetworkProvider(NetworkType.Regtest); var regtestNetworkProvider = new BTCPayNetworkProvider(NetworkType.Regtest);
var mainnetNetworkProvider = new BTCPayNetworkProvider(NetworkType.Mainnet); var mainnetNetworkProvider = new BTCPayNetworkProvider(NetworkType.Mainnet);
var testnetParser = new DerivationSchemeParser(testnetNetworkProvider.GetNetwork("BTC")); var testnetParser = new DerivationSchemeParser(testnetNetworkProvider.GetNetwork<BTCPayNetwork>("BTC"));
var mainnetParser = new DerivationSchemeParser(mainnetNetworkProvider.GetNetwork("BTC")); var mainnetParser = new DerivationSchemeParser(mainnetNetworkProvider.GetNetwork<BTCPayNetwork>("BTC"));
NBXplorer.DerivationStrategy.DerivationStrategyBase result; NBXplorer.DerivationStrategy.DerivationStrategyBase result;
// Passing electrum stuff // Passing electrum stuff
// Passing a native segwit from mainnet to a testnet parser, means the testnet parser will try to convert it into segwit // Passing a native segwit from mainnet to a testnet parser, means the testnet parser will try to convert it into segwit
@@ -1543,16 +1543,16 @@ namespace BTCPayServer.Tests
result = testnetParser.Parse(tpub); result = testnetParser.Parse(tpub);
Assert.Equal($"{tpub}-[p2sh]", result.ToString()); Assert.Equal($"{tpub}-[p2sh]", result.ToString());
var regtestParser = new DerivationSchemeParser(regtestNetworkProvider.GetNetwork("BTC")); var regtestParser = new DerivationSchemeParser(regtestNetworkProvider.GetNetwork<BTCPayNetwork>("BTC"));
var parsed = regtestParser.Parse("xpub6DG1rMYXiQtCc6CfdLFD9CtxqhzzRh7j6Sq6EdE9abgYy3cfDRrniLLv2AdwqHL1exiLnnKR5XXcaoiiexf3Y9R6J6rxkJtqJHzNzMW9QMZ-[p2sh]"); var parsed = regtestParser.Parse("xpub6DG1rMYXiQtCc6CfdLFD9CtxqhzzRh7j6Sq6EdE9abgYy3cfDRrniLLv2AdwqHL1exiLnnKR5XXcaoiiexf3Y9R6J6rxkJtqJHzNzMW9QMZ-[p2sh]");
Assert.Equal("tpubDDdeNbNDRgqestPX5XEJM8ELAq6eR5cne5RPbBHHvWSSiLHNHehsrn1kGCijMnHFSsFFQMqHcdMfGzDL3pWHRasPMhcGRqZ4tFankQ3i4ok-[p2sh]", parsed.ToString()); Assert.Equal("tpubDDdeNbNDRgqestPX5XEJM8ELAq6eR5cne5RPbBHHvWSSiLHNHehsrn1kGCijMnHFSsFFQMqHcdMfGzDL3pWHRasPMhcGRqZ4tFankQ3i4ok-[p2sh]", parsed.ToString());
// Let's make sure we can't generate segwit with dogecoin // Let's make sure we can't generate segwit with dogecoin
regtestParser = new DerivationSchemeParser(regtestNetworkProvider.GetNetwork("DOGE")); regtestParser = new DerivationSchemeParser(regtestNetworkProvider.GetNetwork<BTCPayNetwork>("DOGE"));
parsed = regtestParser.Parse("xpub6DG1rMYXiQtCc6CfdLFD9CtxqhzzRh7j6Sq6EdE9abgYy3cfDRrniLLv2AdwqHL1exiLnnKR5XXcaoiiexf3Y9R6J6rxkJtqJHzNzMW9QMZ-[p2sh]"); parsed = regtestParser.Parse("xpub6DG1rMYXiQtCc6CfdLFD9CtxqhzzRh7j6Sq6EdE9abgYy3cfDRrniLLv2AdwqHL1exiLnnKR5XXcaoiiexf3Y9R6J6rxkJtqJHzNzMW9QMZ-[p2sh]");
Assert.Equal("tpubDDdeNbNDRgqestPX5XEJM8ELAq6eR5cne5RPbBHHvWSSiLHNHehsrn1kGCijMnHFSsFFQMqHcdMfGzDL3pWHRasPMhcGRqZ4tFankQ3i4ok-[legacy]", parsed.ToString()); Assert.Equal("tpubDDdeNbNDRgqestPX5XEJM8ELAq6eR5cne5RPbBHHvWSSiLHNHehsrn1kGCijMnHFSsFFQMqHcdMfGzDL3pWHRasPMhcGRqZ4tFankQ3i4ok-[legacy]", parsed.ToString());
regtestParser = new DerivationSchemeParser(regtestNetworkProvider.GetNetwork("DOGE")); regtestParser = new DerivationSchemeParser(regtestNetworkProvider.GetNetwork<BTCPayNetwork>("DOGE"));
parsed = regtestParser.Parse("tpubDDdeNbNDRgqestPX5XEJM8ELAq6eR5cne5RPbBHHvWSSiLHNHehsrn1kGCijMnHFSsFFQMqHcdMfGzDL3pWHRasPMhcGRqZ4tFankQ3i4ok-[p2sh]"); parsed = regtestParser.Parse("tpubDDdeNbNDRgqestPX5XEJM8ELAq6eR5cne5RPbBHHvWSSiLHNHehsrn1kGCijMnHFSsFFQMqHcdMfGzDL3pWHRasPMhcGRqZ4tFankQ3i4ok-[p2sh]");
Assert.Equal("tpubDDdeNbNDRgqestPX5XEJM8ELAq6eR5cne5RPbBHHvWSSiLHNHehsrn1kGCijMnHFSsFFQMqHcdMfGzDL3pWHRasPMhcGRqZ4tFankQ3i4ok-[legacy]", parsed.ToString()); Assert.Equal("tpubDDdeNbNDRgqestPX5XEJM8ELAq6eR5cne5RPbBHHvWSSiLHNHehsrn1kGCijMnHFSsFFQMqHcdMfGzDL3pWHRasPMhcGRqZ4tFankQ3i4ok-[legacy]", parsed.ToString());
} }
@@ -1569,7 +1569,7 @@ namespace BTCPayServer.Tests
user.RegisterDerivationScheme("BTC"); user.RegisterDerivationScheme("BTC");
user.RegisterDerivationScheme("LTC"); user.RegisterDerivationScheme("LTC");
user.RegisterLightningNode("BTC", LightningConnectionType.CLightning); user.RegisterLightningNode("BTC", LightningConnectionType.CLightning);
var btcNetwork = tester.PayTester.Networks.GetNetwork("BTC"); var btcNetwork = tester.PayTester.Networks.GetNetwork<BTCPayNetwork>("BTC");
var invoice = user.BitPay.CreateInvoice(new Invoice() var invoice = user.BitPay.CreateInvoice(new Invoice()
{ {
Price = 1.5m, Price = 1.5m,
@@ -2709,7 +2709,7 @@ donation:
[Trait("Fast", "Fast")] [Trait("Fast", "Fast")]
public void ParseDerivationSchemeSettings() public void ParseDerivationSchemeSettings()
{ {
var mainnet = new BTCPayNetworkProvider(NetworkType.Mainnet).GetNetwork("BTC"); var mainnet = new BTCPayNetworkProvider(NetworkType.Mainnet).GetNetwork<BTCPayNetwork>("BTC");
var root = new Mnemonic("usage fever hen zero slide mammal silent heavy donate budget pulse say brain thank sausage brand craft about save attract muffin advance illegal cabbage").DeriveExtKey(); var root = new Mnemonic("usage fever hen zero slide mammal silent heavy donate budget pulse say brain thank sausage brand craft about save attract muffin advance illegal cabbage").DeriveExtKey();
Assert.True(DerivationSchemeSettings.TryParseFromColdcard("{\"keystore\": {\"ckcc_xpub\": \"xpub661MyMwAqRbcGVBsTGeNZN6QGVHmMHLdSA4FteGsRrEriu4pnVZMZWnruFFFXkMnyoBjyHndD3Qwcfz4MPzBUxjSevweNFQx7SAYZATtcDw\", \"xpub\": \"ypub6WWc2gWwHbdnAAyJDnR4SPL1phRh7REqrPBfZeizaQ1EmTshieRXJC3Z5YoU4wkcdKHEjQGkh6AYEzCQC1Kz3DNaWSwdc1pc8416hAjzqyD\", \"label\": \"Coldcard Import 0x60d1af8b\", \"ckcc_xfp\": 1624354699, \"type\": \"hardware\", \"hw_type\": \"coldcard\", \"derivation\": \"m/49'/0'/0'\"}, \"wallet_type\": \"standard\", \"use_encryption\": false, \"seed_version\": 17}", mainnet, out var settings)); Assert.True(DerivationSchemeSettings.TryParseFromColdcard("{\"keystore\": {\"ckcc_xpub\": \"xpub661MyMwAqRbcGVBsTGeNZN6QGVHmMHLdSA4FteGsRrEriu4pnVZMZWnruFFFXkMnyoBjyHndD3Qwcfz4MPzBUxjSevweNFQx7SAYZATtcDw\", \"xpub\": \"ypub6WWc2gWwHbdnAAyJDnR4SPL1phRh7REqrPBfZeizaQ1EmTshieRXJC3Z5YoU4wkcdKHEjQGkh6AYEzCQC1Kz3DNaWSwdc1pc8416hAjzqyD\", \"label\": \"Coldcard Import 0x60d1af8b\", \"ckcc_xfp\": 1624354699, \"type\": \"hardware\", \"hw_type\": \"coldcard\", \"derivation\": \"m/49'/0'/0'\"}, \"wallet_type\": \"standard\", \"use_encryption\": false, \"seed_version\": 17}", mainnet, out var settings));
Assert.Equal(root.GetPublicKey().GetHDFingerPrint(), settings.AccountKeySettings[0].RootFingerprint); Assert.Equal(root.GetPublicKey().GetHDFingerPrint(), settings.AccountKeySettings[0].RootFingerprint);
@@ -2719,7 +2719,7 @@ donation:
Assert.Equal("ypub6WWc2gWwHbdnAAyJDnR4SPL1phRh7REqrPBfZeizaQ1EmTshieRXJC3Z5YoU4wkcdKHEjQGkh6AYEzCQC1Kz3DNaWSwdc1pc8416hAjzqyD", settings.AccountOriginal); Assert.Equal("ypub6WWc2gWwHbdnAAyJDnR4SPL1phRh7REqrPBfZeizaQ1EmTshieRXJC3Z5YoU4wkcdKHEjQGkh6AYEzCQC1Kz3DNaWSwdc1pc8416hAjzqyD", settings.AccountOriginal);
Assert.Equal(root.Derive(new KeyPath("m/49'/0'/0'")).Neuter().PubKey.WitHash.ScriptPubKey.Hash.ScriptPubKey, settings.AccountDerivation.Derive(new KeyPath()).ScriptPubKey); Assert.Equal(root.Derive(new KeyPath("m/49'/0'/0'")).Neuter().PubKey.WitHash.ScriptPubKey.Hash.ScriptPubKey, settings.AccountDerivation.Derive(new KeyPath()).ScriptPubKey);
var testnet = new BTCPayNetworkProvider(NetworkType.Testnet).GetNetwork("BTC"); var testnet = new BTCPayNetworkProvider(NetworkType.Testnet).GetNetwork<BTCPayNetwork>("BTC");
// Should be legacy // Should be legacy
Assert.True(DerivationSchemeSettings.TryParseFromColdcard("{\"keystore\": {\"ckcc_xpub\": \"tpubD6NzVbkrYhZ4YHNiuTdTmHRmbcPRLfqgyneZFCL1mkzkUBjXriQShxTh9HL34FK2mhieasJVk9EzJrUfkFqRNQBjiXgx3n5BhPkxKBoFmaS\", \"xpub\": \"tpubDDWYqT3P24znfsaGX7kZcQhNc5LAjnQiKQvUCHF2jS6dsgJBRtymopEU5uGpMaR5YChjuiExZG1X2aTbqXkp82KqH5qnqwWHp6EWis9ZvKr\", \"label\": \"Coldcard Import 0x60d1af8b\", \"ckcc_xfp\": 1624354699, \"type\": \"hardware\", \"hw_type\": \"coldcard\", \"derivation\": \"m/44'/1'/0'\"}, \"wallet_type\": \"standard\", \"use_encryption\": false, \"seed_version\": 17}", testnet, out settings)); Assert.True(DerivationSchemeSettings.TryParseFromColdcard("{\"keystore\": {\"ckcc_xpub\": \"tpubD6NzVbkrYhZ4YHNiuTdTmHRmbcPRLfqgyneZFCL1mkzkUBjXriQShxTh9HL34FK2mhieasJVk9EzJrUfkFqRNQBjiXgx3n5BhPkxKBoFmaS\", \"xpub\": \"tpubDDWYqT3P24znfsaGX7kZcQhNc5LAjnQiKQvUCHF2jS6dsgJBRtymopEU5uGpMaR5YChjuiExZG1X2aTbqXkp82KqH5qnqwWHp6EWis9ZvKr\", \"label\": \"Coldcard Import 0x60d1af8b\", \"ckcc_xfp\": 1624354699, \"type\": \"hardware\", \"hw_type\": \"coldcard\", \"derivation\": \"m/44'/1'/0'\"}, \"wallet_type\": \"standard\", \"use_encryption\": false, \"seed_version\": 17}", testnet, out settings));

View File

@@ -81,12 +81,12 @@ namespace BTCPayServer.Configuration
NetworkProvider = new BTCPayNetworkProvider(NetworkType).Filter(supportedChains.ToArray()); NetworkProvider = new BTCPayNetworkProvider(NetworkType).Filter(supportedChains.ToArray());
foreach (var chain in supportedChains) foreach (var chain in supportedChains)
{ {
if (NetworkProvider.GetNetwork(chain) == null) if (NetworkProvider.GetNetwork<BTCPayNetworkBase>(chain) == null)
throw new ConfigException($"Invalid chains \"{chain}\""); throw new ConfigException($"Invalid chains \"{chain}\"");
} }
var validChains = new List<string>(); var validChains = new List<string>();
foreach (var net in NetworkProvider.GetAll()) foreach (var net in NetworkProvider.GetAll().OfType<BTCPayNetwork>())
{ {
NBXplorerConnectionSetting setting = new NBXplorerConnectionSetting(); NBXplorerConnectionSetting setting = new NBXplorerConnectionSetting();
setting.CryptoCode = net.CryptoCode; setting.CryptoCode = net.CryptoCode;

View File

@@ -46,7 +46,7 @@ namespace BTCPayServer.Configuration
app.Option("--debuglog", "A rolling log file for debug messages.", CommandOptionType.SingleValue); app.Option("--debuglog", "A rolling log file for debug messages.", CommandOptionType.SingleValue);
app.Option("--debugloglevel", "The severity you log (default:information)", CommandOptionType.SingleValue); app.Option("--debugloglevel", "The severity you log (default:information)", CommandOptionType.SingleValue);
app.Option("--disable-registration", "Disables new user registrations (default:true)", CommandOptionType.SingleValue); app.Option("--disable-registration", "Disables new user registrations (default:true)", CommandOptionType.SingleValue);
foreach (var network in provider.GetAll()) foreach (var network in provider.GetAll().OfType<BTCPayNetwork>())
{ {
var crypto = network.CryptoCode.ToLowerInvariant(); var crypto = network.CryptoCode.ToLowerInvariant();
app.Option($"--{crypto}explorerurl", $"URL of the NBXplorer for {network.CryptoCode} (default: {network.NBXplorerNetwork.DefaultSettings.DefaultUrl})", CommandOptionType.SingleValue); app.Option($"--{crypto}explorerurl", $"URL of the NBXplorer for {network.CryptoCode} (default: {network.NBXplorerNetwork.DefaultSettings.DefaultUrl})", CommandOptionType.SingleValue);
@@ -121,7 +121,7 @@ namespace BTCPayServer.Configuration
builder.AppendLine("#mysql=User ID=root;Password=myPassword;Host=localhost;Port=3306;Database=myDataBase;"); builder.AppendLine("#mysql=User ID=root;Password=myPassword;Host=localhost;Port=3306;Database=myDataBase;");
builder.AppendLine(); builder.AppendLine();
builder.AppendLine("### NBXplorer settings ###"); builder.AppendLine("### NBXplorer settings ###");
foreach (var n in new BTCPayNetworkProvider(networkType).GetAll()) foreach (var n in new BTCPayNetworkProvider(networkType).GetAll().OfType<BTCPayNetwork>())
{ {
builder.AppendLine($"#{n.CryptoCode}.explorer.url={n.NBXplorerNetwork.DefaultSettings.DefaultUrl}"); builder.AppendLine($"#{n.CryptoCode}.explorer.url={n.NBXplorerNetwork.DefaultSettings.DefaultUrl}");
builder.AppendLine($"#{n.CryptoCode}.explorer.cookiefile={ n.NBXplorerNetwork.DefaultSettings.DefaultCookieFile}"); builder.AppendLine($"#{n.CryptoCode}.explorer.cookiefile={ n.NBXplorerNetwork.DefaultSettings.DefaultCookieFile}");

View File

@@ -91,7 +91,7 @@ namespace BTCPayServer.Controllers
return View(model); return View(model);
} }
//TODO: abstract
private InvoiceDetailsModel InvoicePopulatePayments(InvoiceEntity invoice) private InvoiceDetailsModel InvoicePopulatePayments(InvoiceEntity invoice)
{ {
var model = new InvoiceDetailsModel(); var model = new InvoiceDetailsModel();
@@ -117,8 +117,14 @@ namespace BTCPayServer.Controllers
foreach (var payment in invoice.GetPayments()) foreach (var payment in invoice.GetPayments())
{ {
var paymentNetwork = _NetworkProvider.GetNetwork(payment.GetCryptoCode()); //TODO: abstract
var paymentNetwork = _NetworkProvider.GetNetwork<BTCPayNetwork>(payment.GetCryptoCode());
if (paymentNetwork == null)
{
continue;
}
var paymentData = payment.GetCryptoPaymentData(); var paymentData = payment.GetCryptoPaymentData();
//TODO: abstract
if (paymentData is Payments.Bitcoin.BitcoinLikePaymentData onChainPaymentData) if (paymentData is Payments.Bitcoin.BitcoinLikePaymentData onChainPaymentData)
{ {
var m = new InvoiceDetailsModel.Payment(); var m = new InvoiceDetailsModel.Payment();
@@ -236,10 +242,10 @@ namespace BTCPayServer.Controllers
paymentMethodId = store.GetDefaultPaymentId(_NetworkProvider); paymentMethodId = store.GetDefaultPaymentId(_NetworkProvider);
isDefaultPaymentId = true; isDefaultPaymentId = true;
} }
var network = _NetworkProvider.GetNetwork(paymentMethodId.CryptoCode); BTCPayNetworkBase network = _NetworkProvider.GetNetwork<BTCPayNetwork>(paymentMethodId.CryptoCode);
if (network == null && isDefaultPaymentId) if (network == null && isDefaultPaymentId)
{ {
network = _NetworkProvider.GetAll().FirstOrDefault(); network = _NetworkProvider.GetAll().OfType<BTCPayNetwork>().FirstOrDefault();
paymentMethodId = new PaymentMethodId(network.CryptoCode, PaymentTypes.BTCLike); paymentMethodId = new PaymentMethodId(network.CryptoCode, PaymentTypes.BTCLike);
} }
if (invoice == null || network == null) if (invoice == null || network == null)
@@ -352,16 +358,17 @@ namespace BTCPayServer.Controllers
return model; return model;
} }
private string GetDisplayName(PaymentMethodId paymentMethodId, BTCPayNetwork network) private string GetDisplayName(PaymentMethodId paymentMethodId, BTCPayNetworkBase network)
{ {
return paymentMethodId.PaymentType == PaymentTypes.BTCLike ? return paymentMethodId.PaymentType == PaymentTypes.BTCLike ?
network.DisplayName : network.DisplayName + " (Lightning)"; network.DisplayName : network.DisplayName + " (Lightning)";
} }
private string GetImage(PaymentMethodId paymentMethodId, BTCPayNetwork network) private string GetImage(PaymentMethodId paymentMethodId, BTCPayNetworkBase network)
{ {
//the direct casting ((BTCPayNetwork)network) ) for ln image is only temp..this method is offloaded to payment handlers in other pull requests
return paymentMethodId.PaymentType == PaymentTypes.BTCLike ? return paymentMethodId.PaymentType == PaymentTypes.BTCLike ?
this.Request.GetRelativePathOrAbsolute(network.CryptoImagePath) : this.Request.GetRelativePathOrAbsolute(network.LightningImagePath); this.Request.GetRelativePathOrAbsolute(network.CryptoImagePath) : this.Request.GetRelativePathOrAbsolute(((BTCPayNetwork)network).LightningImagePath);
} }
private string OrderAmountFromInvoice(string cryptoCode, ProductInformation productInformation) private string OrderAmountFromInvoice(string cryptoCode, ProductInformation productInformation)

View File

@@ -152,7 +152,7 @@ namespace BTCPayServer.Controllers
foreach (var network in store.GetSupportedPaymentMethods(_NetworkProvider) foreach (var network in store.GetSupportedPaymentMethods(_NetworkProvider)
.Where(s => !excludeFilter.Match(s.PaymentId)) .Where(s => !excludeFilter.Match(s.PaymentId))
.Select(c => _NetworkProvider.GetNetwork(c.PaymentId.CryptoCode)) .Select(c => _NetworkProvider.GetNetwork<BTCPayNetworkBase>(c.PaymentId.CryptoCode))
.Where(c => c != null)) .Where(c => c != null))
{ {
currencyPairsToFetch.Add(new CurrencyPair(network.CryptoCode, invoice.Currency)); currencyPairsToFetch.Add(new CurrencyPair(network.CryptoCode, invoice.Currency));
@@ -170,7 +170,7 @@ namespace BTCPayServer.Controllers
.Select(c => .Select(c =>
(Handler: (IPaymentMethodHandler)_ServiceProvider.GetService(typeof(IPaymentMethodHandler<>).MakeGenericType(c.GetType())), (Handler: (IPaymentMethodHandler)_ServiceProvider.GetService(typeof(IPaymentMethodHandler<>).MakeGenericType(c.GetType())),
SupportedPaymentMethod: c, SupportedPaymentMethod: c,
Network: _NetworkProvider.GetNetwork(c.PaymentId.CryptoCode))) Network: _NetworkProvider.GetNetwork<BTCPayNetworkBase>(c.PaymentId.CryptoCode)))
.Where(c => c.Network != null) .Where(c => c.Network != null)
.Select(o => .Select(o =>
(SupportedPaymentMethod: o.SupportedPaymentMethod, (SupportedPaymentMethod: o.SupportedPaymentMethod,
@@ -247,7 +247,7 @@ namespace BTCPayServer.Controllers
}).ToArray()); }).ToArray());
} }
private async Task<PaymentMethod> CreatePaymentMethodAsync(Dictionary<CurrencyPair, Task<RateResult>> fetchingByCurrencyPair, IPaymentMethodHandler handler, ISupportedPaymentMethod supportedPaymentMethod, BTCPayNetwork network, InvoiceEntity entity, StoreData store, InvoiceLogs logs) private async Task<PaymentMethod> CreatePaymentMethodAsync(Dictionary<CurrencyPair, Task<RateResult>> fetchingByCurrencyPair, IPaymentMethodHandler handler, ISupportedPaymentMethod supportedPaymentMethod, BTCPayNetworkBase network, InvoiceEntity entity, StoreData store, InvoiceLogs logs)
{ {
try try
{ {

View File

@@ -41,7 +41,7 @@ namespace BTCPayServer.Controllers
try try
{ {
var paymentMethodDetails = GetExistingLightningSupportedPaymentMethod(cryptoCode, store); var paymentMethodDetails = GetExistingLightningSupportedPaymentMethod(cryptoCode, store);
var network = _BtcPayNetworkProvider.GetNetwork(cryptoCode); var network = _BtcPayNetworkProvider.GetNetwork<BTCPayNetwork>(cryptoCode);
var nodeInfo = var nodeInfo =
await _LightningLikePaymentHandler.GetNodeInfo(this.Request.IsOnion(), paymentMethodDetails, await _LightningLikePaymentHandler.GetNodeInfo(this.Request.IsOnion(), paymentMethodDetails,
network); network);

View File

@@ -66,7 +66,7 @@ namespace BTCPayServer.Controllers
var webSocket = await HttpContext.WebSockets.AcceptWebSocketAsync(); var webSocket = await HttpContext.WebSockets.AcceptWebSocketAsync();
var hw = new LedgerHardwareWalletService(webSocket); var hw = new LedgerHardwareWalletService(webSocket);
object result = null; object result = null;
var network = _NetworkProvider.GetNetwork(cryptoCode); var network = _NetworkProvider.GetNetwork<BTCPayNetwork>(cryptoCode);
using (var normalOperationTimeout = new CancellationTokenSource()) using (var normalOperationTimeout = new CancellationTokenSource())
{ {

View File

@@ -152,7 +152,7 @@ namespace BTCPayServer.Controllers
ModelState.AddModelError(nameof(vm.ConnectionString), "Missing url parameter"); ModelState.AddModelError(nameof(vm.ConnectionString), "Missing url parameter");
return View(vm); return View(vm);
case "test": case "test":
var handler = (LightningLikePaymentHandler)_ServiceProvider.GetRequiredService<IPaymentMethodHandler<Payments.Lightning.LightningSupportedPaymentMethod>>(); var handler = _ServiceProvider.GetRequiredService<LightningLikePaymentHandler>();
try try
{ {
var info = await handler.GetNodeInfo(this.Request.IsOnion(), paymentMethod, network); var info = await handler.GetNodeInfo(this.Request.IsOnion(), paymentMethod, network);

View File

@@ -372,7 +372,7 @@ namespace BTCPayServer.Controllers
private string GetDisplayName(PaymentMethodId paymentMethodId) private string GetDisplayName(PaymentMethodId paymentMethodId)
{ {
var display = _NetworkProvider.GetNetwork(paymentMethodId.CryptoCode)?.DisplayName ?? paymentMethodId.CryptoCode; var display = _NetworkProvider.GetNetwork<BTCPayNetworkBase>(paymentMethodId.CryptoCode)?.DisplayName ?? paymentMethodId.CryptoCode;
return paymentMethodId.PaymentType == PaymentTypes.BTCLike ? return paymentMethodId.PaymentType == PaymentTypes.BTCLike ?
display : $"{display} (Lightning)"; display : $"{display} (Lightning)";
} }

View File

@@ -52,7 +52,7 @@ namespace BTCPayServer.Controllers
public async Task<IActionResult> WalletPSBT([ModelBinder(typeof(WalletIdModelBinder))] public async Task<IActionResult> WalletPSBT([ModelBinder(typeof(WalletIdModelBinder))]
WalletId walletId, WalletPSBTViewModel vm) WalletId walletId, WalletPSBTViewModel vm)
{ {
var network = NetworkProvider.GetNetwork(walletId.CryptoCode); var network = NetworkProvider.GetNetwork<BTCPayNetwork>(walletId.CryptoCode);
if (await vm.GetPSBT(network.NBitcoinNetwork) is PSBT psbt) if (await vm.GetPSBT(network.NBitcoinNetwork) is PSBT psbt)
{ {
vm.Decoded = psbt.ToString(); vm.Decoded = psbt.ToString();
@@ -67,7 +67,7 @@ namespace BTCPayServer.Controllers
WalletId walletId, WalletId walletId,
WalletPSBTViewModel vm, string command = null) WalletPSBTViewModel vm, string command = null)
{ {
var network = NetworkProvider.GetNetwork(walletId.CryptoCode); var network = NetworkProvider.GetNetwork<BTCPayNetwork>(walletId.CryptoCode);
var psbt = await vm.GetPSBT(network.NBitcoinNetwork); var psbt = await vm.GetPSBT(network.NBitcoinNetwork);
if (psbt == null) if (psbt == null)
{ {
@@ -110,7 +110,7 @@ namespace BTCPayServer.Controllers
string signingKey = null, string signingKey = null,
string signingKeyPath = null) string signingKeyPath = null)
{ {
var network = NetworkProvider.GetNetwork(walletId.CryptoCode); var network = NetworkProvider.GetNetwork<BTCPayNetwork>(walletId.CryptoCode);
var vm = new WalletPSBTReadyViewModel() { PSBT = psbt }; var vm = new WalletPSBTReadyViewModel() { PSBT = psbt };
vm.SigningKey = signingKey; vm.SigningKey = signingKey;
vm.SigningKeyPath = signingKeyPath; vm.SigningKeyPath = signingKeyPath;
@@ -209,7 +209,7 @@ namespace BTCPayServer.Controllers
WalletId walletId, WalletPSBTReadyViewModel vm, string command = null) WalletId walletId, WalletPSBTReadyViewModel vm, string command = null)
{ {
PSBT psbt = null; PSBT psbt = null;
var network = NetworkProvider.GetNetwork(walletId.CryptoCode); var network = NetworkProvider.GetNetwork<BTCPayNetwork>(walletId.CryptoCode);
try try
{ {
psbt = PSBT.Parse(vm.PSBT, network.NBitcoinNetwork); psbt = PSBT.Parse(vm.PSBT, network.NBitcoinNetwork);
@@ -286,7 +286,7 @@ namespace BTCPayServer.Controllers
public async Task<IActionResult> WalletPSBTCombine([ModelBinder(typeof(WalletIdModelBinder))] public async Task<IActionResult> WalletPSBTCombine([ModelBinder(typeof(WalletIdModelBinder))]
WalletId walletId, WalletPSBTCombineViewModel vm) WalletId walletId, WalletPSBTCombineViewModel vm)
{ {
var network = NetworkProvider.GetNetwork(walletId.CryptoCode); var network = NetworkProvider.GetNetwork<BTCPayNetwork>(walletId.CryptoCode);
var psbt = await vm.GetPSBT(network.NBitcoinNetwork); var psbt = await vm.GetPSBT(network.NBitcoinNetwork);
if (psbt == null) if (psbt == null)
{ {

View File

@@ -156,7 +156,7 @@ namespace BTCPayServer.Controllers
DerivationSchemeSettings paymentMethod = GetDerivationSchemeSettings(walletId, store); DerivationSchemeSettings paymentMethod = GetDerivationSchemeSettings(walletId, store);
if (paymentMethod == null) if (paymentMethod == null)
return NotFound(); return NotFound();
var network = this.NetworkProvider.GetNetwork(walletId?.CryptoCode); var network = this.NetworkProvider.GetNetwork<BTCPayNetwork>(walletId?.CryptoCode);
if (network == null) if (network == null)
return NotFound(); return NotFound();
var storeData = store.GetStoreBlob(); var storeData = store.GetStoreBlob();
@@ -218,7 +218,7 @@ namespace BTCPayServer.Controllers
var store = await Repository.FindStore(walletId.StoreId, GetUserId()); var store = await Repository.FindStore(walletId.StoreId, GetUserId());
if (store == null) if (store == null)
return NotFound(); return NotFound();
var network = this.NetworkProvider.GetNetwork(walletId?.CryptoCode); var network = this.NetworkProvider.GetNetwork<BTCPayNetwork>(walletId?.CryptoCode);
if (network == null) if (network == null)
return NotFound(); return NotFound();
vm.SupportRBF = network.SupportRBF; vm.SupportRBF = network.SupportRBF;
@@ -360,7 +360,7 @@ namespace BTCPayServer.Controllers
{ {
return View(viewModel); return View(viewModel);
} }
var network = NetworkProvider.GetNetwork(walletId.CryptoCode); var network = NetworkProvider.GetNetwork<BTCPayNetwork>(walletId.CryptoCode);
if (network == null) if (network == null)
throw new FormatException("Invalid value for crypto code"); throw new FormatException("Invalid value for crypto code");
@@ -413,7 +413,7 @@ namespace BTCPayServer.Controllers
return await WalletPSBTReady(walletId, psbt.ToBase64(), signingKey.GetWif(network.NBitcoinNetwork).ToString(), rootedKeyPath.ToString()); return await WalletPSBTReady(walletId, psbt.ToBase64(), signingKey.GetWif(network.NBitcoinNetwork).ToString(), rootedKeyPath.ToString());
} }
private string ValueToString(Money v, BTCPayNetwork network) private string ValueToString(Money v, BTCPayNetworkBase network)
{ {
return v.ToString() + " " + network.CryptoCode; return v.ToString() + " " + network.CryptoCode;
} }
@@ -433,7 +433,7 @@ namespace BTCPayServer.Controllers
private async Task<IActionResult> RedirectToWalletTransaction(WalletId walletId, Transaction transaction) private async Task<IActionResult> RedirectToWalletTransaction(WalletId walletId, Transaction transaction)
{ {
var network = NetworkProvider.GetNetwork(walletId.CryptoCode); var network = NetworkProvider.GetNetwork<BTCPayNetwork>(walletId.CryptoCode);
if (transaction != null) if (transaction != null)
{ {
var wallet = _walletProvider.GetWallet(network); var wallet = _walletProvider.GetWallet(network);
@@ -578,7 +578,7 @@ namespace BTCPayServer.Controllers
if (!HttpContext.WebSockets.IsWebSocketRequest) if (!HttpContext.WebSockets.IsWebSocketRequest)
return NotFound(); return NotFound();
var network = NetworkProvider.GetNetwork(walletId.CryptoCode); var network = NetworkProvider.GetNetwork<BTCPayNetwork>(walletId.CryptoCode);
if (network == null) if (network == null)
throw new FormatException("Invalid value for crypto code"); throw new FormatException("Invalid value for crypto code");
var storeData = (await Repository.FindStore(walletId.StoreId, GetUserId())); var storeData = (await Repository.FindStore(walletId.StoreId, GetUserId()));

View File

@@ -84,7 +84,7 @@ namespace BTCPayServer.Data
foreach (var strat in strategies.Properties()) foreach (var strat in strategies.Properties())
{ {
var paymentMethodId = PaymentMethodId.Parse(strat.Name); var paymentMethodId = PaymentMethodId.Parse(strat.Name);
var network = networks.GetNetwork(paymentMethodId.CryptoCode); var network = networks.GetNetwork<BTCPayNetwork>(paymentMethodId.CryptoCode);
if (network != null) if (network != null)
{ {
if (network == networks.BTC && paymentMethodId.PaymentType == PaymentTypes.BTCLike && btcReturned) if (network == networks.BTC && paymentMethodId.PaymentType == PaymentTypes.BTCLike && btcReturned)
@@ -282,7 +282,7 @@ namespace BTCPayServer.Data
public double Multiplier { get; set; } public double Multiplier { get; set; }
public decimal Apply(BTCPayNetwork network, decimal rate) public decimal Apply(BTCPayNetworkBase network, decimal rate)
{ {
return rate * (decimal)Multiplier; return rate * (decimal)Multiplier;
} }

View File

@@ -7,7 +7,7 @@ namespace BTCPayServer.Events
{ {
public class InvoiceNewAddressEvent public class InvoiceNewAddressEvent
{ {
public InvoiceNewAddressEvent(string invoiceId, string address, BTCPayNetwork network) public InvoiceNewAddressEvent(string invoiceId, string address, BTCPayNetworkBase network)
{ {
Address = address; Address = address;
InvoiceId = invoiceId; InvoiceId = invoiceId;
@@ -16,7 +16,7 @@ namespace BTCPayServer.Events
public string Address { get; set; } public string Address { get; set; }
public string InvoiceId { get; set; } public string InvoiceId { get; set; }
public BTCPayNetwork Network { get; set; } public BTCPayNetworkBase Network { get; set; }
public override string ToString() public override string ToString()
{ {
return $"{Network.CryptoCode}: New address {Address} for invoice {InvoiceId}"; return $"{Network.CryptoCode}: New address {Address} for invoice {InvoiceId}";

View File

@@ -8,14 +8,14 @@ namespace BTCPayServer.Events
{ {
public class NBXplorerStateChangedEvent public class NBXplorerStateChangedEvent
{ {
public NBXplorerStateChangedEvent(BTCPayNetwork network, NBXplorerState old, NBXplorerState newState) public NBXplorerStateChangedEvent(BTCPayNetworkBase network, NBXplorerState old, NBXplorerState newState)
{ {
Network = network; Network = network;
NewState = newState; NewState = newState;
OldState = old; OldState = old;
} }
public BTCPayNetwork Network { get; set; } public BTCPayNetworkBase Network { get; set; }
public NBXplorerState NewState { get; set; } public NBXplorerState NewState { get; set; }
public NBXplorerState OldState { get; set; } public NBXplorerState OldState { get; set; }

View File

@@ -33,7 +33,7 @@ namespace BTCPayServer
Logs.Configuration.LogInformation($"{setting.CryptoCode}: Cookie file is {(setting.CookieFile ?? "not set")}"); Logs.Configuration.LogInformation($"{setting.CryptoCode}: Cookie file is {(setting.CookieFile ?? "not set")}");
if (setting.ExplorerUri != null) if (setting.ExplorerUri != null)
{ {
_Clients.TryAdd(setting.CryptoCode, CreateExplorerClient(httpClientFactory.CreateClient($"NBXPLORER_{setting.CryptoCode}"), _NetworkProviders.GetNetwork(setting.CryptoCode), setting.ExplorerUri, setting.CookieFile)); _Clients.TryAdd(setting.CryptoCode, CreateExplorerClient(httpClientFactory.CreateClient($"NBXPLORER_{setting.CryptoCode}"), _NetworkProviders.GetNetwork<BTCPayNetwork>(setting.CryptoCode), setting.ExplorerUri, setting.CookieFile));
} }
} }
} }
@@ -58,21 +58,21 @@ namespace BTCPayServer
public ExplorerClient GetExplorerClient(string cryptoCode) public ExplorerClient GetExplorerClient(string cryptoCode)
{ {
var network = _NetworkProviders.GetNetwork(cryptoCode); var network = _NetworkProviders.GetNetwork<BTCPayNetwork>(cryptoCode);
if (network == null) if (network == null)
return null; return null;
_Clients.TryGetValue(network.CryptoCode, out ExplorerClient client); _Clients.TryGetValue(network.CryptoCode, out ExplorerClient client);
return client; return client;
} }
public ExplorerClient GetExplorerClient(BTCPayNetwork network) public ExplorerClient GetExplorerClient(BTCPayNetworkBase network)
{ {
if (network == null) if (network == null)
throw new ArgumentNullException(nameof(network)); throw new ArgumentNullException(nameof(network));
return GetExplorerClient(network.CryptoCode); return GetExplorerClient(network.CryptoCode);
} }
public bool IsAvailable(BTCPayNetwork network) public bool IsAvailable(BTCPayNetworkBase network)
{ {
return IsAvailable(network.CryptoCode); return IsAvailable(network.CryptoCode);
} }
@@ -84,7 +84,7 @@ namespace BTCPayServer
public BTCPayNetwork GetNetwork(string cryptoCode) public BTCPayNetwork GetNetwork(string cryptoCode)
{ {
var network = _NetworkProviders.GetNetwork(cryptoCode); var network = _NetworkProviders.GetNetwork<BTCPayNetwork>(cryptoCode);
if (network == null) if (network == null)
return null; return null;
if (_Clients.ContainsKey(network.CryptoCode)) if (_Clients.ContainsKey(network.CryptoCode))
@@ -94,7 +94,7 @@ namespace BTCPayServer
public IEnumerable<(BTCPayNetwork, ExplorerClient)> GetAll() public IEnumerable<(BTCPayNetwork, ExplorerClient)> GetAll()
{ {
foreach (var net in _NetworkProviders.GetAll()) foreach (var net in _NetworkProviders.GetAll().OfType<BTCPayNetwork>())
{ {
if (_Clients.TryGetValue(net.CryptoCode, out ExplorerClient explorer)) if (_Clients.TryGetValue(net.CryptoCode, out ExplorerClient explorer))
{ {

View File

@@ -78,7 +78,7 @@ namespace BTCPayServer.HostedServices
var paymentMethod = GetNearestClearedPayment(allPaymentMethods, out var accounting, _NetworkProvider); var paymentMethod = GetNearestClearedPayment(allPaymentMethods, out var accounting, _NetworkProvider);
if (paymentMethod == null) if (paymentMethod == null)
return; return;
var network = _NetworkProvider.GetNetwork(paymentMethod.GetId().CryptoCode); var network = _NetworkProvider.GetNetwork<BTCPayNetworkBase>(paymentMethod.GetId().CryptoCode);
if (invoice.Status == InvoiceStatus.New || invoice.Status == InvoiceStatus.Expired) if (invoice.Status == InvoiceStatus.New || invoice.Status == InvoiceStatus.Expired)
{ {
if (accounting.Paid >= accounting.MinimumTotalDue) if (accounting.Paid >= accounting.MinimumTotalDue)
@@ -173,7 +173,7 @@ namespace BTCPayServer.HostedServices
decimal nearestToZero = 0.0m; decimal nearestToZero = 0.0m;
foreach (var paymentMethod in allPaymentMethods) foreach (var paymentMethod in allPaymentMethods)
{ {
if (networkProvider != null && networkProvider.GetNetwork(paymentMethod.GetId().CryptoCode) == null) if (networkProvider != null && networkProvider.GetNetwork<BTCPayNetworkBase>(paymentMethod.GetId().CryptoCode) == null)
continue; continue;
var currentAccounting = paymentMethod.Calculate(); var currentAccounting = paymentMethod.Calculate();
var distanceFromZero = Math.Abs(currentAccounting.DueUncapped.ToDecimal(MoneyUnit.BTC)); var distanceFromZero = Math.Abs(currentAccounting.DueUncapped.ToDecimal(MoneyUnit.BTC));
@@ -324,7 +324,7 @@ namespace BTCPayServer.HostedServices
.GetPayments() .GetPayments()
.Select<PaymentEntity, Task<PaymentEntity>>(async payment => .Select<PaymentEntity, Task<PaymentEntity>>(async payment =>
{ {
var paymentNetwork = _NetworkProvider.GetNetwork(payment.GetCryptoCode()); var paymentNetwork = _NetworkProvider.GetNetwork<BTCPayNetwork>(payment.GetCryptoCode());
var paymentData = payment.GetCryptoPaymentData(); var paymentData = payment.GetCryptoPaymentData();
if (paymentData is Payments.Bitcoin.BitcoinLikePaymentData onChainPaymentData) if (paymentData is Payments.Bitcoin.BitcoinLikePaymentData onChainPaymentData)
{ {

View File

@@ -24,13 +24,13 @@ namespace BTCPayServer.HostedServices
{ {
public class NBXplorerSummary public class NBXplorerSummary
{ {
public BTCPayNetwork Network { get; set; } public BTCPayNetworkBase Network { get; set; }
public NBXplorerState State { get; set; } public NBXplorerState State { get; set; }
public StatusResult Status { get; set; } public StatusResult Status { get; set; }
public string Error { get; set; } public string Error { get; set; }
} }
ConcurrentDictionary<string, NBXplorerSummary> _Summaries = new ConcurrentDictionary<string, NBXplorerSummary>(); ConcurrentDictionary<string, NBXplorerSummary> _Summaries = new ConcurrentDictionary<string, NBXplorerSummary>();
public void Publish(BTCPayNetwork network, NBXplorerState state, StatusResult status, string error) public void Publish(BTCPayNetworkBase network, NBXplorerState state, StatusResult status, string error)
{ {
var summary = new NBXplorerSummary() { Network = network, State = state, Status = status, Error = error }; var summary = new NBXplorerSummary() { Network = network, State = state, Status = status, Error = error };
_Summaries.AddOrUpdate(network.CryptoCode, summary, (k, v) => summary); _Summaries.AddOrUpdate(network.CryptoCode, summary, (k, v) => summary);

View File

@@ -39,7 +39,7 @@ namespace BTCPayServer.ModelBinders
var networkProvider = (BTCPayNetworkProvider)bindingContext.HttpContext.RequestServices.GetService(typeof(BTCPayNetworkProvider)); var networkProvider = (BTCPayNetworkProvider)bindingContext.HttpContext.RequestServices.GetService(typeof(BTCPayNetworkProvider));
var cryptoCode = bindingContext.ValueProvider.GetValue("cryptoCode").FirstValue; var cryptoCode = bindingContext.ValueProvider.GetValue("cryptoCode").FirstValue;
var network = networkProvider.GetNetwork(cryptoCode ?? "BTC"); var network = networkProvider.GetNetwork<BTCPayNetwork>(cryptoCode ?? "BTC");
try try
{ {
var data = new DerivationStrategyFactory(network.NBitcoinNetwork).Parse(key); var data = new DerivationStrategyFactory(network.NBitcoinNetwork).Parse(key);

View File

@@ -104,7 +104,8 @@ namespace BTCPayServer.PaymentRequest
Status = entity.GetInvoiceState().ToString(), Status = entity.GetInvoiceState().ToString(),
Payments = entity.GetPayments().Select(paymentEntity => Payments = entity.GetPayments().Select(paymentEntity =>
{ {
var paymentNetwork = _BtcPayNetworkProvider.GetNetwork(paymentEntity.GetCryptoCode()); //TODO: abstract
var paymentNetwork = _BtcPayNetworkProvider.GetNetwork<BTCPayNetworkBase>(paymentEntity.GetCryptoCode());
var paymentData = paymentEntity.GetCryptoPaymentData(); var paymentData = paymentEntity.GetCryptoPaymentData();
string link = null; string link = null;
string txId = null; string txId = null;

View File

@@ -54,12 +54,12 @@ namespace BTCPayServer.Payments.Bitcoin
return Output.Value.ToDecimal(MoneyUnit.BTC); return Output.Value.ToDecimal(MoneyUnit.BTC);
} }
public bool PaymentCompleted(PaymentEntity entity, BTCPayNetwork network) public bool PaymentCompleted(PaymentEntity entity, BTCPayNetworkBase network)
{ {
return ConfirmationCount >= network.MaxTrackedConfirmation; return ConfirmationCount >= network.MaxTrackedConfirmation;
} }
public bool PaymentConfirmed(PaymentEntity entity, SpeedPolicy speedPolicy, BTCPayNetwork network) public bool PaymentConfirmed(PaymentEntity entity, SpeedPolicy speedPolicy, BTCPayNetworkBase network)
{ {
if (speedPolicy == SpeedPolicy.HighSpeed) if (speedPolicy == SpeedPolicy.HighSpeed)
{ {
@@ -80,12 +80,12 @@ namespace BTCPayServer.Payments.Bitcoin
return false; return false;
} }
public BitcoinAddress GetDestination(BTCPayNetwork network) public BitcoinAddress GetDestination(BTCPayNetworkBase network)
{ {
return Output.ScriptPubKey.GetDestinationAddress(network.NBitcoinNetwork); return Output.ScriptPubKey.GetDestinationAddress(((BTCPayNetwork)network).NBitcoinNetwork);
} }
string CryptoPaymentData.GetDestination(BTCPayNetwork network) string CryptoPaymentData.GetDestination(BTCPayNetworkBase network)
{ {
return GetDestination(network).ToString(); return GetDestination(network).ToString();
} }

View File

@@ -33,7 +33,7 @@ namespace BTCPayServer.Payments.Bitcoin
public Task<BitcoinAddress> ReserveAddress; public Task<BitcoinAddress> ReserveAddress;
} }
public override object PreparePayment(DerivationSchemeSettings supportedPaymentMethod, StoreData store, BTCPayNetwork network) public override object PreparePayment(DerivationSchemeSettings supportedPaymentMethod, StoreData store, BTCPayNetworkBase network)
{ {
return new Prepare() return new Prepare()
{ {
@@ -45,7 +45,9 @@ namespace BTCPayServer.Payments.Bitcoin
public override string PrettyDescription => "On-Chain"; public override string PrettyDescription => "On-Chain";
public override PaymentTypes PaymentType => PaymentTypes.BTCLike; public override PaymentTypes PaymentType => PaymentTypes.BTCLike;
public override async Task<IPaymentMethodDetails> CreatePaymentMethodDetails(DerivationSchemeSettings supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store, BTCPayNetwork network, object preparePaymentObject) public override async Task<IPaymentMethodDetails> CreatePaymentMethodDetails(
DerivationSchemeSettings supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store,
BTCPayNetworkBase network, object preparePaymentObject)
{ {
if (!_ExplorerProvider.IsAvailable(network)) if (!_ExplorerProvider.IsAvailable(network))
throw new PaymentMethodUnavailableException($"Full node not available"); throw new PaymentMethodUnavailableException($"Full node not available");

View File

@@ -310,7 +310,7 @@ namespace BTCPayServer.Payments.Bitcoin
return new TransactionConflicts(conflictsByOutpoint.Where(c => c.Value.Transactions.Count > 1).Select(c => c.Value)); return new TransactionConflicts(conflictsByOutpoint.Where(c => c.Value.Transactions.Count > 1).Select(c => c.Value));
} }
private async Task<int> FindPaymentViaPolling(BTCPayWallet wallet, BTCPayNetwork network) private async Task<int> FindPaymentViaPolling(BTCPayWallet wallet, BTCPayNetworkBase network)
{ {
int totalPayment = 0; int totalPayment = 0;
var invoices = await _InvoiceRepository.GetPendingInvoices(); var invoices = await _InvoiceRepository.GetPendingInvoices();
@@ -347,7 +347,7 @@ namespace BTCPayServer.Payments.Bitcoin
return totalPayment; return totalPayment;
} }
private DerivationStrategyBase GetDerivationStrategy(InvoiceEntity invoice, BTCPayNetwork network) private DerivationStrategyBase GetDerivationStrategy(InvoiceEntity invoice, BTCPayNetworkBase network)
{ {
return invoice.GetSupportedPaymentMethod<DerivationSchemeSettings>(new PaymentMethodId(network.CryptoCode, PaymentTypes.BTCLike)) return invoice.GetSupportedPaymentMethod<DerivationSchemeSettings>(new PaymentMethodId(network.CryptoCode, PaymentTypes.BTCLike))
.Select(d => d.AccountDerivation) .Select(d => d.AccountDerivation)

View File

@@ -19,8 +19,9 @@ namespace BTCPayServer.Payments
/// <param name="paymentMethod"></param> /// <param name="paymentMethod"></param>
/// <param name="store"></param> /// <param name="store"></param>
/// <param name="network"></param> /// <param name="network"></param>
/// <param name="preparePaymentObject"></param>
/// <returns></returns> /// <returns></returns>
Task<IPaymentMethodDetails> CreatePaymentMethodDetails(ISupportedPaymentMethod supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store, BTCPayNetwork network, object preparePaymentObject); Task<IPaymentMethodDetails> CreatePaymentMethodDetails(ISupportedPaymentMethod supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store, BTCPayNetworkBase network, object preparePaymentObject);
/// <summary> /// <summary>
/// This method called before the rate have been fetched /// This method called before the rate have been fetched
@@ -29,7 +30,7 @@ namespace BTCPayServer.Payments
/// <param name="store"></param> /// <param name="store"></param>
/// <param name="network"></param> /// <param name="network"></param>
/// <returns></returns> /// <returns></returns>
object PreparePayment(ISupportedPaymentMethod supportedPaymentMethod, StoreData store, BTCPayNetwork network); object PreparePayment(ISupportedPaymentMethod supportedPaymentMethod, StoreData store, BTCPayNetworkBase network);
bool CanHandle(PaymentMethodId paymentMethodId); bool CanHandle(PaymentMethodId paymentMethodId);
@@ -38,20 +39,23 @@ namespace BTCPayServer.Payments
public interface IPaymentMethodHandler<T> : IPaymentMethodHandler where T : ISupportedPaymentMethod public interface IPaymentMethodHandler<T> : IPaymentMethodHandler where T : ISupportedPaymentMethod
{ {
Task<IPaymentMethodDetails> CreatePaymentMethodDetails(T supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store, BTCPayNetwork network, object preparePaymentObject); Task<IPaymentMethodDetails> CreatePaymentMethodDetails(T supportedPaymentMethod, PaymentMethod paymentMethod,
StoreData store, BTCPayNetworkBase network, object preparePaymentObject);
} }
public abstract class PaymentMethodHandlerBase<T> : IPaymentMethodHandler<T> where T : ISupportedPaymentMethod public abstract class PaymentMethodHandlerBase<T> : IPaymentMethodHandler<T> where T : ISupportedPaymentMethod
{ {
public abstract string PrettyDescription { get; } public abstract string PrettyDescription { get; }
public abstract PaymentTypes PaymentType { get; } public abstract PaymentTypes PaymentType { get; }
public abstract Task<IPaymentMethodDetails> CreatePaymentMethodDetails(T supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store, BTCPayNetwork network, object preparePaymentObject); public abstract Task<IPaymentMethodDetails> CreatePaymentMethodDetails(T supportedPaymentMethod,
public virtual object PreparePayment(T supportedPaymentMethod, StoreData store, BTCPayNetwork network) PaymentMethod paymentMethod, StoreData store, BTCPayNetworkBase network, object preparePaymentObject);
public virtual object PreparePayment(T supportedPaymentMethod, StoreData store, BTCPayNetworkBase network)
{ {
return null; return null;
} }
object IPaymentMethodHandler.PreparePayment(ISupportedPaymentMethod supportedPaymentMethod, StoreData store, BTCPayNetwork network) object IPaymentMethodHandler.PreparePayment(ISupportedPaymentMethod supportedPaymentMethod, StoreData store,
BTCPayNetworkBase network)
{ {
if (supportedPaymentMethod is T method) if (supportedPaymentMethod is T method)
{ {
@@ -70,7 +74,9 @@ namespace BTCPayServer.Payments
return $"{paymentMethodId.CryptoCode} ({PrettyDescription})"; return $"{paymentMethodId.CryptoCode} ({PrettyDescription})";
} }
Task<IPaymentMethodDetails> IPaymentMethodHandler.CreatePaymentMethodDetails(ISupportedPaymentMethod supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store, BTCPayNetwork network, object preparePaymentObject) Task<IPaymentMethodDetails> IPaymentMethodHandler.CreatePaymentMethodDetails(
ISupportedPaymentMethod supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store,
BTCPayNetworkBase network, object preparePaymentObject)
{ {
if (supportedPaymentMethod is T method) if (supportedPaymentMethod is T method)
{ {

View File

@@ -20,7 +20,7 @@ namespace BTCPayServer.Payments.Lightning
[JsonConverter(typeof(NBitcoin.JsonConverters.UInt256JsonConverter))] [JsonConverter(typeof(NBitcoin.JsonConverters.UInt256JsonConverter))]
public uint256 PaymentHash { get; set; } public uint256 PaymentHash { get; set; }
public string GetDestination(BTCPayNetwork network) public string GetDestination(BTCPayNetworkBase network)
{ {
return BOLT11; return BOLT11;
} }
@@ -49,12 +49,12 @@ namespace BTCPayServer.Payments.Lightning
return Amount.ToDecimal(LightMoneyUnit.BTC); return Amount.ToDecimal(LightMoneyUnit.BTC);
} }
public bool PaymentCompleted(PaymentEntity entity, BTCPayNetwork network) public bool PaymentCompleted(PaymentEntity entity, BTCPayNetworkBase network)
{ {
return true; return true;
} }
public bool PaymentConfirmed(PaymentEntity entity, SpeedPolicy speedPolicy, BTCPayNetwork network) public bool PaymentConfirmed(PaymentEntity entity, SpeedPolicy speedPolicy, BTCPayNetworkBase network)
{ {
return true; return true;
} }

View File

@@ -34,13 +34,16 @@ namespace BTCPayServer.Payments.Lightning
public override string PrettyDescription => "Off-Chain"; public override string PrettyDescription => "Off-Chain";
public override PaymentTypes PaymentType => PaymentTypes.LightningLike; public override PaymentTypes PaymentType => PaymentTypes.LightningLike;
public override async Task<IPaymentMethodDetails> CreatePaymentMethodDetails(LightningSupportedPaymentMethod supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store, BTCPayNetwork network, object preparePaymentObject) public override async Task<IPaymentMethodDetails> CreatePaymentMethodDetails(
LightningSupportedPaymentMethod supportedPaymentMethod, PaymentMethod paymentMethod, StoreData store,
BTCPayNetworkBase network, object preparePaymentObject)
{ {
//direct casting to (BTCPayNetwork) is fixed in other pull requests with better generic interfacing for handlers
var storeBlob = store.GetStoreBlob(); var storeBlob = store.GetStoreBlob();
var test = GetNodeInfo(paymentMethod.PreferOnion, supportedPaymentMethod, network); var test = GetNodeInfo(paymentMethod.PreferOnion, supportedPaymentMethod, (BTCPayNetwork)network);
var invoice = paymentMethod.ParentEntity; var invoice = paymentMethod.ParentEntity;
var due = Extensions.RoundUp(invoice.ProductInformation.Price / paymentMethod.Rate, 8); var due = Extensions.RoundUp(invoice.ProductInformation.Price / paymentMethod.Rate, 8);
var client = _lightningClientFactory.Create(supportedPaymentMethod.GetLightningUrl(), network); var client = _lightningClientFactory.Create(supportedPaymentMethod.GetLightningUrl(), (BTCPayNetwork)network);
var expiry = invoice.ExpirationTime - DateTimeOffset.UtcNow; var expiry = invoice.ExpirationTime - DateTimeOffset.UtcNow;
if (expiry < TimeSpan.Zero) if (expiry < TimeSpan.Zero)
expiry = TimeSpan.FromSeconds(1); expiry = TimeSpan.FromSeconds(1);

View File

@@ -105,7 +105,7 @@ namespace BTCPayServer.Payments.Lightning
.FirstOrDefault(c => c.CryptoCode == paymentMethod.GetId().CryptoCode); .FirstOrDefault(c => c.CryptoCode == paymentMethod.GetId().CryptoCode);
if (lightningSupportedMethod == null) if (lightningSupportedMethod == null)
continue; continue;
var network = _NetworkProvider.GetNetwork(paymentMethod.GetId().CryptoCode); var network = _NetworkProvider.GetNetwork<BTCPayNetwork>(paymentMethod.GetId().CryptoCode);
listenedInvoices.Add(new ListenedInvoice() listenedInvoices.Add(new ListenedInvoice()
{ {

View File

@@ -10,20 +10,21 @@ namespace BTCPayServer.Payments
{ {
public class PaymentMethodExtensions public class PaymentMethodExtensions
{ {
public static ISupportedPaymentMethod Deserialize(PaymentMethodId paymentMethodId, JToken value, BTCPayNetwork network) public static ISupportedPaymentMethod Deserialize(PaymentMethodId paymentMethodId, JToken value, BTCPayNetworkBase network)
{ {
if (paymentMethodId.PaymentType == PaymentTypes.BTCLike) if (paymentMethodId.PaymentType == PaymentTypes.BTCLike)
{ {
var bitcoinSpecificBtcPayNetwork = (BTCPayNetwork)network;
if (value is JObject jobj) if (value is JObject jobj)
{ {
var scheme = network.NBXplorerNetwork.Serializer.ToObject<DerivationSchemeSettings>(jobj); var scheme = bitcoinSpecificBtcPayNetwork.NBXplorerNetwork.Serializer.ToObject<DerivationSchemeSettings>(jobj);
scheme.Network = network; scheme.Network = bitcoinSpecificBtcPayNetwork;
return scheme; return scheme;
} }
// Legacy // Legacy
else else
{ {
return BTCPayServer.DerivationSchemeSettings.Parse(((JValue)value).Value<string>(), network); return BTCPayServer.DerivationSchemeSettings.Parse(((JValue)value).Value<string>(), bitcoinSpecificBtcPayNetwork);
} }
} }
////////// //////////

View File

@@ -7,6 +7,6 @@ namespace BTCPayServer.Services
{ {
public interface IFeeProviderFactory public interface IFeeProviderFactory
{ {
IFeeProvider CreateFeeProvider(BTCPayNetwork network); IFeeProvider CreateFeeProvider(BTCPayNetworkBase network);
} }
} }

View File

@@ -21,7 +21,7 @@ namespace BTCPayServer.Services.Fees
public FeeRate Fallback { get; set; } public FeeRate Fallback { get; set; }
public int BlockTarget { get; set; } public int BlockTarget { get; set; }
public IFeeProvider CreateFeeProvider(BTCPayNetwork network) public IFeeProvider CreateFeeProvider(BTCPayNetworkBase network)
{ {
return new NBXplorerFeeProvider(this, _ExplorerClients.GetExplorerClient(network)); return new NBXplorerFeeProvider(this, _ExplorerClients.GetExplorerClient(network));
} }

View File

@@ -78,7 +78,7 @@ namespace BTCPayServer.Services.Invoices.Export
CryptoCode = cryptoCode, CryptoCode = cryptoCode,
ConversionRate = pmethod.Rate, ConversionRate = pmethod.Rate,
PaymentType = payment.GetPaymentMethodId().PaymentType == Payments.PaymentTypes.BTCLike ? "OnChain" : "OffChain", PaymentType = payment.GetPaymentMethodId().PaymentType == Payments.PaymentTypes.BTCLike ? "OnChain" : "OffChain",
Destination = payment.GetCryptoPaymentData().GetDestination(Networks.GetNetwork(cryptoCode)), Destination = payment.GetCryptoPaymentData().GetDestination(Networks.GetNetwork<BTCPayNetworkBase>(cryptoCode)),
Paid = pdata.GetValue().ToString(CultureInfo.InvariantCulture), Paid = pdata.GetValue().ToString(CultureInfo.InvariantCulture),
PaidCurrency = Math.Round(pdata.GetValue() * pmethod.Rate, currency.NumberDecimalDigits).ToString(CultureInfo.InvariantCulture), PaidCurrency = Math.Round(pdata.GetValue() * pmethod.Rate, currency.NumberDecimalDigits).ToString(CultureInfo.InvariantCulture),
// Adding NetworkFee because Paid doesn't take into account network fees // Adding NetworkFee because Paid doesn't take into account network fees

View File

@@ -213,7 +213,7 @@ namespace BTCPayServer.Services.Invoices
foreach (var strat in strategies.Properties()) foreach (var strat in strategies.Properties())
{ {
var paymentMethodId = PaymentMethodId.Parse(strat.Name); var paymentMethodId = PaymentMethodId.Parse(strat.Name);
var network = Networks.GetNetwork(paymentMethodId.CryptoCode); var network = Networks.GetNetwork<BTCPayNetwork>(paymentMethodId.CryptoCode);
if (network != null) if (network != null)
{ {
if (network == Networks.BTC && paymentMethodId.PaymentType == PaymentTypes.BTCLike) if (network == Networks.BTC && paymentMethodId.PaymentType == PaymentTypes.BTCLike)
@@ -280,7 +280,7 @@ namespace BTCPayServer.Services.Invoices
{ {
return Payments.Where(p => p.CryptoCode == cryptoCode).ToList(); return Payments.Where(p => p.CryptoCode == cryptoCode).ToList();
} }
public List<PaymentEntity> GetPayments(BTCPayNetwork network) public List<PaymentEntity> GetPayments(BTCPayNetworkBase network)
{ {
return GetPayments(network.CryptoCode); return GetPayments(network.CryptoCode);
} }
@@ -521,7 +521,7 @@ namespace BTCPayServer.Services.Invoices
GetPaymentMethods().TryGetValue(paymentMethodId, out var data); GetPaymentMethods().TryGetValue(paymentMethodId, out var data);
return data; return data;
} }
public PaymentMethod GetPaymentMethod(BTCPayNetwork network, PaymentTypes paymentType, BTCPayNetworkProvider networkProvider) public PaymentMethod GetPaymentMethod(BTCPayNetworkBase network, PaymentTypes paymentType, BTCPayNetworkProvider networkProvider)
{ {
return GetPaymentMethod(new PaymentMethodId(network.CryptoCode, paymentType), networkProvider); return GetPaymentMethod(new PaymentMethodId(network.CryptoCode, paymentType), networkProvider);
} }
@@ -540,7 +540,7 @@ namespace BTCPayServer.Services.Invoices
r.CryptoCode = paymentMethodId.CryptoCode; r.CryptoCode = paymentMethodId.CryptoCode;
r.PaymentType = paymentMethodId.PaymentType.ToString(); r.PaymentType = paymentMethodId.PaymentType.ToString();
r.ParentEntity = this; r.ParentEntity = this;
r.Network = Networks?.GetNetwork(r.CryptoCode); r.Network = Networks?.GetNetwork<BTCPayNetworkBase>(r.CryptoCode);
if (r.Network != null || Networks == null) if (r.Network != null || Networks == null)
paymentMethods.Add(r); paymentMethods.Add(r);
} }
@@ -732,7 +732,7 @@ namespace BTCPayServer.Services.Invoices
[JsonIgnore] [JsonIgnore]
public InvoiceEntity ParentEntity { get; set; } public InvoiceEntity ParentEntity { get; set; }
[JsonIgnore] [JsonIgnore]
public BTCPayNetwork Network { get; set; } public BTCPayNetworkBase Network { get; set; }
[JsonProperty(PropertyName = "cryptoCode", DefaultValueHandling = DefaultValueHandling.Ignore)] [JsonProperty(PropertyName = "cryptoCode", DefaultValueHandling = DefaultValueHandling.Ignore)]
[Obsolete("Use GetId().CryptoCode instead")] [Obsolete("Use GetId().CryptoCode instead")]
public string CryptoCode { get; set; } public string CryptoCode { get; set; }
@@ -1026,10 +1026,10 @@ namespace BTCPayServer.Services.Invoices
/// </summary> /// </summary>
/// <returns>The amount paid</returns> /// <returns>The amount paid</returns>
decimal GetValue(); decimal GetValue();
bool PaymentCompleted(PaymentEntity entity, BTCPayNetwork network); bool PaymentCompleted(PaymentEntity entity, BTCPayNetworkBase network);
bool PaymentConfirmed(PaymentEntity entity, SpeedPolicy speedPolicy, BTCPayNetwork network); bool PaymentConfirmed(PaymentEntity entity, SpeedPolicy speedPolicy, BTCPayNetworkBase network);
PaymentTypes GetPaymentType(); PaymentTypes GetPaymentType();
string GetDestination(BTCPayNetwork network); string GetDestination(BTCPayNetworkBase network);
} }
} }

View File

@@ -137,7 +137,7 @@ retry:
public async Task<InvoiceEntity> CreateInvoiceAsync(string storeId, InvoiceEntity invoice) public async Task<InvoiceEntity> CreateInvoiceAsync(string storeId, InvoiceEntity invoice)
{ {
List<string> textSearch = new List<string>(); List<string> textSearch = new List<string>();
invoice = NBitcoin.JsonConverters.Serializer.ToObject<InvoiceEntity>(ToString(invoice, null), null); invoice = ToObject(ToBytes(invoice));
invoice.Networks = _Networks; invoice.Networks = _Networks;
invoice.Id = Encoders.Base58.EncodeData(RandomUtils.GetBytes(16)); invoice.Id = Encoders.Base58.EncodeData(RandomUtils.GetBytes(16));
#pragma warning disable CS0618 #pragma warning disable CS0618
@@ -166,7 +166,7 @@ retry:
throw new InvalidOperationException("CryptoCode unsupported"); throw new InvalidOperationException("CryptoCode unsupported");
var paymentDestination = paymentMethod.GetPaymentMethodDetails().GetPaymentDestination(); var paymentDestination = paymentMethod.GetPaymentMethodDetails().GetPaymentDestination();
string address = GetDestination(paymentMethod, paymentMethod.Network.NBitcoinNetwork); string address = GetDestination(paymentMethod);
context.AddressInvoices.Add(new AddressInvoiceData() context.AddressInvoices.Add(new AddressInvoiceData()
{ {
InvoiceDataId = invoice.Id, InvoiceDataId = invoice.Id,
@@ -215,18 +215,19 @@ retry:
} }
} }
private static string GetDestination(PaymentMethod paymentMethod, Network network) private string GetDestination(PaymentMethod paymentMethod)
{ {
// For legacy reason, BitcoinLikeOnChain is putting the hashes of addresses in database // For legacy reason, BitcoinLikeOnChain is putting the hashes of addresses in database
if (paymentMethod.GetId().PaymentType == Payments.PaymentTypes.BTCLike) if (paymentMethod.GetId().PaymentType == Payments.PaymentTypes.BTCLike)
{ {
return ((Payments.Bitcoin.BitcoinLikeOnChainPaymentMethod)paymentMethod.GetPaymentMethodDetails()).GetDepositAddress(network).ScriptPubKey.Hash.ToString(); var network = (BTCPayNetwork)paymentMethod.Network;
return ((Payments.Bitcoin.BitcoinLikeOnChainPaymentMethod)paymentMethod.GetPaymentMethodDetails()).GetDepositAddress(network.NBitcoinNetwork).ScriptPubKey.Hash.ToString();
} }
/////////////// ///////////////
return paymentMethod.GetPaymentMethodDetails().GetPaymentDestination(); return paymentMethod.GetPaymentMethodDetails().GetPaymentDestination();
} }
public async Task<bool> NewAddress(string invoiceId, Payments.Bitcoin.BitcoinLikeOnChainPaymentMethod paymentMethod, BTCPayNetwork network) public async Task<bool> NewAddress(string invoiceId, Payments.Bitcoin.BitcoinLikeOnChainPaymentMethod paymentMethod, BTCPayNetworkBase network)
{ {
using (var context = _ContextFactory.CreateContext()) using (var context = _ContextFactory.CreateContext())
{ {
@@ -254,14 +255,14 @@ retry:
} }
#pragma warning restore CS0618 #pragma warning restore CS0618
invoiceEntity.SetPaymentMethod(currencyData); invoiceEntity.SetPaymentMethod(currencyData);
invoice.Blob = ToBytes(invoiceEntity, network.NBitcoinNetwork); invoice.Blob = ToBytes(invoiceEntity, network);
context.AddressInvoices.Add(new AddressInvoiceData() context.AddressInvoices.Add(new AddressInvoiceData()
{ {
InvoiceDataId = invoiceId, InvoiceDataId = invoiceId,
CreatedTime = DateTimeOffset.UtcNow CreatedTime = DateTimeOffset.UtcNow
} }
.Set(GetDestination(currencyData, network.NBitcoinNetwork), currencyData.GetId())); .Set(GetDestination(currencyData), currencyData.GetId()));
context.HistoricalAddressInvoices.Add(new HistoricalAddressInvoiceData() context.HistoricalAddressInvoices.Add(new HistoricalAddressInvoiceData()
{ {
InvoiceDataId = invoiceId, InvoiceDataId = invoiceId,
@@ -592,7 +593,7 @@ retry:
return status; return status;
} }
public async Task AddRefundsAsync(string invoiceId, TxOut[] outputs, Network network) public async Task AddRefundsAsync(string invoiceId, TxOut[] outputs, BTCPayNetwork network)
{ {
if (outputs.Length == 0) if (outputs.Length == 0)
return; return;
@@ -613,7 +614,7 @@ retry:
await context.SaveChangesAsync().ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false);
} }
var addresses = outputs.Select(o => o.ScriptPubKey.GetDestinationAddress(network)).Where(a => a != null).ToArray(); var addresses = outputs.Select(o => o.ScriptPubKey.GetDestinationAddress(network.NBitcoinNetwork)).Where(a => a != null).ToArray();
AddToTextSearch(invoiceId, addresses.Select(a => a.ToString()).ToArray()); AddToTextSearch(invoiceId, addresses.Select(a => a.ToString()).ToArray());
} }
@@ -626,7 +627,7 @@ retry:
/// <param name="cryptoCode"></param> /// <param name="cryptoCode"></param>
/// <param name="accounted"></param> /// <param name="accounted"></param>
/// <returns>The PaymentEntity or null if already added</returns> /// <returns>The PaymentEntity or null if already added</returns>
public async Task<PaymentEntity> AddPayment(string invoiceId, DateTimeOffset date, CryptoPaymentData paymentData, BTCPayNetwork network, bool accounted = false) public async Task<PaymentEntity> AddPayment(string invoiceId, DateTimeOffset date, CryptoPaymentData paymentData, BTCPayNetworkBase network, bool accounted = false)
{ {
using (var context = _ContextFactory.CreateContext()) using (var context = _ContextFactory.CreateContext())
{ {
@@ -655,7 +656,7 @@ retry:
bitcoinPaymentMethod.NextNetworkFee = bitcoinPaymentMethod.FeeRate.GetFee(100); // assume price for 100 bytes bitcoinPaymentMethod.NextNetworkFee = bitcoinPaymentMethod.FeeRate.GetFee(100); // assume price for 100 bytes
paymentMethod.SetPaymentMethodDetails(bitcoinPaymentMethod); paymentMethod.SetPaymentMethodDetails(bitcoinPaymentMethod);
invoiceEntity.SetPaymentMethod(paymentMethod); invoiceEntity.SetPaymentMethod(paymentMethod);
invoice.Blob = ToBytes(invoiceEntity, network.NBitcoinNetwork); invoice.Blob = ToBytes(invoiceEntity, network);
} }
PaymentData data = new PaymentData PaymentData data = new PaymentData
{ {
@@ -704,20 +705,27 @@ retry:
entity.Networks = _Networks; entity.Networks = _Networks;
return entity; return entity;
} }
private T ToObject<T>(byte[] value, Network network) private T ToObject<T>(byte[] value, BTCPayNetworkBase network)
{ {
return NBitcoin.JsonConverters.Serializer.ToObject<T>(ZipUtils.Unzip(value), network); if (network == null)
{
return NBitcoin.JsonConverters.Serializer.ToObject<T>(ZipUtils.Unzip(value), null);
}
return network.ToObject<T>(ZipUtils.Unzip(value));
} }
private byte[] ToBytes<T>(T obj, BTCPayNetworkBase network = null)
private byte[] ToBytes<T>(T obj, Network network)
{ {
return ZipUtils.Zip(NBitcoin.JsonConverters.Serializer.ToString(obj, network)); return ZipUtils.Zip(ToString(obj, network));
} }
private string ToString<T>(T data, Network network) private string ToString<T>(T data, BTCPayNetworkBase network)
{ {
return NBitcoin.JsonConverters.Serializer.ToString(data, network); if (network == null)
{
return NBitcoin.JsonConverters.Serializer.ToString(data, null);
}
return network.ToString(data);
} }
public void Dispose() public void Dispose()

View File

@@ -80,13 +80,13 @@ namespace BTCPayServer.Services
Services = result.ToArray(); Services = result.ToArray();
} }
private bool TryParseP2PService(string name, out BTCPayNetwork network) private bool TryParseP2PService(string name, out BTCPayNetworkBase network)
{ {
network = null; network = null;
var splitted = name.Trim().Split('-'); var splitted = name.Trim().Split('-');
if (splitted.Length != 2 || splitted[1] != "P2P") if (splitted.Length != 2 || splitted[1] != "P2P")
return false; return false;
network = _networks.GetNetwork(splitted[0]); network = _networks.GetNetwork<BTCPayNetworkBase>(splitted[0]);
return network != null; return network != null;
} }
} }
@@ -94,7 +94,7 @@ namespace BTCPayServer.Services
public class TorService public class TorService
{ {
public TorServiceType ServiceType { get; set; } = TorServiceType.Other; public TorServiceType ServiceType { get; set; } = TorServiceType.Other;
public BTCPayNetwork Network { get; set; } public BTCPayNetworkBase Network { get; set; }
public string Name { get; set; } public string Name { get; set; }
public string OnionHost { get; set; } public string OnionHost { get; set; }
public int VirtualPort { get; set; } public int VirtualPort { get; set; }

View File

@@ -22,7 +22,7 @@ namespace BTCPayServer.Services.Wallets
_NetworkProvider = networkProvider; _NetworkProvider = networkProvider;
_Options = memoryCacheOption; _Options = memoryCacheOption;
foreach(var network in networkProvider.GetAll()) foreach(var network in networkProvider.GetAll().OfType<BTCPayNetwork>())
{ {
var explorerClient = _Client.GetExplorerClient(network.CryptoCode); var explorerClient = _Client.GetExplorerClient(network.CryptoCode);
if (explorerClient == null) if (explorerClient == null)
@@ -33,7 +33,7 @@ namespace BTCPayServer.Services.Wallets
Dictionary<string, BTCPayWallet> _Wallets = new Dictionary<string, BTCPayWallet>(); Dictionary<string, BTCPayWallet> _Wallets = new Dictionary<string, BTCPayWallet>();
public BTCPayWallet GetWallet(BTCPayNetwork network) public BTCPayWallet GetWallet(BTCPayNetworkBase network)
{ {
if (network == null) if (network == null)
throw new ArgumentNullException(nameof(network)); throw new ArgumentNullException(nameof(network));
@@ -47,7 +47,7 @@ namespace BTCPayServer.Services.Wallets
return result; return result;
} }
public bool IsAvailable(BTCPayNetwork network) public bool IsAvailable(BTCPayNetworkBase network)
{ {
return _Client.IsAvailable(network); return _Client.IsAvailable(network);
} }