diff --git a/Plugins/BTCPayServer.Plugins.Breez/BreezController.cs b/Plugins/BTCPayServer.Plugins.Breez/BreezController.cs index ddf2947..0be705c 100644 --- a/Plugins/BTCPayServer.Plugins.Breez/BreezController.cs +++ b/Plugins/BTCPayServer.Plugins.Breez/BreezController.cs @@ -4,7 +4,6 @@ using System.Linq; using System.Threading.Tasks; using BTCPayServer.Abstractions.Constants; using BTCPayServer.Client; -using BTCPayServer.Plugins.FixedFloat; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Mvc; diff --git a/Plugins/BTCPayServer.Plugins.Breez/BreezLightningClient.cs b/Plugins/BTCPayServer.Plugins.Breez/BreezLightningClient.cs index 5573311..09bb7d5 100644 --- a/Plugins/BTCPayServer.Plugins.Breez/BreezLightningClient.cs +++ b/Plugins/BTCPayServer.Plugins.Breez/BreezLightningClient.cs @@ -4,10 +4,11 @@ using System.Linq; using System.Threading; using System.Threading.Tasks; using Breez.Sdk; +using BTCPayServer.Lightning; using NBitcoin; using Network = Breez.Sdk.Network; -namespace BTCPayServer.Lightning.Breez; +namespace BTCPayServer.Plugins.Breez; public class BreezLightningClient: ILightningClient, IDisposable, EventListener @@ -22,7 +23,7 @@ public class BreezLightningClient: ILightningClient, IDisposable, EventListener new GreenlightNodeConfig(null, inviteCode) ); var config = BreezSdkMethods.DefaultConfig( - EnvironmentType.PRODUCTION, + network ==NBitcoin.Network.Main ? EnvironmentType.PRODUCTION: EnvironmentType.STAGING, apiKey, nodeConfig ) with { diff --git a/Plugins/BTCPayServer.Plugins.Breez/BreezLightningConnectionStringHandler.cs b/Plugins/BTCPayServer.Plugins.Breez/BreezLightningConnectionStringHandler.cs index 22ebcf7..bc44381 100644 --- a/Plugins/BTCPayServer.Plugins.Breez/BreezLightningConnectionStringHandler.cs +++ b/Plugins/BTCPayServer.Plugins.Breez/BreezLightningConnectionStringHandler.cs @@ -1,10 +1,7 @@ -using System; -using System.Linq; -using System.Net.Http; -using BTCPayServer.Plugins.FixedFloat; +using BTCPayServer.Lightning; using NBitcoin; -namespace BTCPayServer.Lightning.Breez; +namespace BTCPayServer.Plugins.Breez; public class BreezLightningConnectionStringHandler : ILightningConnectionStringHandler { diff --git a/Plugins/BTCPayServer.Plugins.Breez/BreezPlugin.cs b/Plugins/BTCPayServer.Plugins.Breez/BreezPlugin.cs new file mode 100644 index 0000000..f36f5a5 --- /dev/null +++ b/Plugins/BTCPayServer.Plugins.Breez/BreezPlugin.cs @@ -0,0 +1,33 @@ +#nullable enable +using BTCPayServer.Abstractions.Contracts; +using BTCPayServer.Abstractions.Models; +using BTCPayServer.Abstractions.Services; +using BTCPayServer.Lightning; +using Microsoft.Extensions.DependencyInjection; +using Microsoft.Extensions.Hosting; + +namespace BTCPayServer.Plugins.Breez +{ + public class BreezPlugin : BaseBTCPayServerPlugin + { + public override IBTCPayServerPlugin.PluginDependency[] Dependencies { get; } = + { + new() {Identifier = nameof(BTCPayServer), Condition = ">=1.12.0"} + }; + + public override void Execute(IServiceCollection applicationBuilder) + { + applicationBuilder.AddSingleton(); + applicationBuilder.AddSingleton(provider => provider.GetRequiredService()); + applicationBuilder.AddSingleton(); + applicationBuilder.AddSingleton(provider => provider.GetRequiredService()); + applicationBuilder.AddSingleton(new UIExtension("Breez/BreezNav", + "store-integrations-nav")); + + applicationBuilder.AddSingleton(new UIExtension("Breez/LNPaymentMethodSetupTabhead", "ln-payment-method-setup-tabhead")); + applicationBuilder.AddSingleton(new UIExtension("Breez/LNPaymentMethodSetupTab", "ln-payment-method-setup-tab")); + + base.Execute(applicationBuilder); + } + } +} \ No newline at end of file diff --git a/Plugins/BTCPayServer.Plugins.Breez/BreezService.cs b/Plugins/BTCPayServer.Plugins.Breez/BreezService.cs new file mode 100644 index 0000000..2745847 --- /dev/null +++ b/Plugins/BTCPayServer.Plugins.Breez/BreezService.cs @@ -0,0 +1,130 @@ +#nullable enable +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Threading; +using System.Threading.Tasks; +using BTCPayServer.Configuration; +using BTCPayServer.Services.Stores; +using Microsoft.Extensions.Hosting; +using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Options; +using NBitcoin; + +namespace BTCPayServer.Plugins.Breez; + +public class BreezService:IHostedService +{ + private readonly StoreRepository _storeRepository; + private readonly IOptions _dataDirectories; + private readonly BTCPayNetworkProvider _btcPayNetworkProvider; + private readonly ILogger _logger; + private Dictionary _settings; + private Dictionary _clients = new(); + + public BreezService(StoreRepository storeRepository, + IOptions dataDirectories, + BTCPayNetworkProvider btcPayNetworkProvider, + ILogger logger) + { + _storeRepository = storeRepository; + _dataDirectories = dataDirectories; + _btcPayNetworkProvider = btcPayNetworkProvider; + _logger = logger; + } + + private string GetWorkDir() + { + var dir = _dataDirectories.Value.DataDir; + return Path.Combine(dir, "Plugins", "Breez"); + } + + TaskCompletionSource tcs = new(); + public async Task StartAsync(CancellationToken cancellationToken) + { + _settings = (await _storeRepository.GetSettingsAsync("Breez")).Where(pair => pair.Value is not null).ToDictionary(pair => pair.Key, pair => pair.Value!); + foreach (var keyValuePair in _settings) + { + try + { + + await Handle(keyValuePair.Key, keyValuePair.Value); + } + catch (Exception e) + { + } + } + tcs.TrySetResult(); + } + + public async Task Get(string storeId) + { + await tcs.Task; + _settings.TryGetValue(storeId, out var settings); + + return settings; + } + + public async Task Handle(string? storeId, BreezSettings? settings) + { + if (settings is null) + { + if (storeId is not null && _clients.Remove(storeId, out var client)) + { + client.Dispose(); + } + } + else + { + try + { + var network = Network.Main; // _btcPayNetworkProvider.BTC.NBitcoinNetwork; + Directory.CreateDirectory(GetWorkDir()); + var client = new BreezLightningClient(settings.InviteCode, settings.ApiKey, GetWorkDir(), + network, settings.Mnemonic); + if (storeId is not null) + { + _clients.AddOrReplace(storeId, client); + } + return client; + } + catch (Exception e) + { + _logger.LogError(e, "Could not create Breez client"); + throw; + } + } + + return null; + } + + public async Task Set(string storeId, BreezSettings? settings) + { + + var result = await Handle(storeId, settings); + await _storeRepository.UpdateSetting(storeId, "Breez", settings!); + if (settings is null) + { + _settings.Remove(storeId); + + } + else if(result is not null ) + { + _settings.AddOrReplace(storeId, settings); + } + + + } + + public async Task StopAsync(CancellationToken cancellationToken) + { + _clients.Values.ToList().ForEach(c => c.Dispose()); + } + + public BreezLightningClient? GetClient(string storeId) + { + _clients.TryGetValue(storeId, out var client); + return client; + } +} \ No newline at end of file diff --git a/Plugins/BTCPayServer.Plugins.Breez/BreezSettings.cs b/Plugins/BTCPayServer.Plugins.Breez/BreezSettings.cs new file mode 100644 index 0000000..297ee8f --- /dev/null +++ b/Plugins/BTCPayServer.Plugins.Breez/BreezSettings.cs @@ -0,0 +1,9 @@ +#nullable enable +namespace BTCPayServer.Plugins.Breez; + +public class BreezSettings +{ + public string InviteCode { get; set; } + public string Mnemonic { get; set; } + public string ApiKey { get; set; } +} \ No newline at end of file diff --git a/Plugins/BTCPayServer.Plugins.Breez/Program.cs b/Plugins/BTCPayServer.Plugins.Breez/Program.cs deleted file mode 100644 index cd9b12c..0000000 --- a/Plugins/BTCPayServer.Plugins.Breez/Program.cs +++ /dev/null @@ -1,149 +0,0 @@ -#nullable enable -using System; -using System.Collections.Generic; -using System.IO; -using System.Linq; -using System.Threading; -using System.Threading.Tasks; -using BTCPayServer.Abstractions.Contracts; -using BTCPayServer.Abstractions.Models; -using BTCPayServer.Abstractions.Services; -using BTCPayServer.Configuration; -using BTCPayServer.Lightning; -using BTCPayServer.Lightning.Breez; -using BTCPayServer.Services.Stores; -using Microsoft.Extensions.DependencyInjection; -using Microsoft.Extensions.Hosting; -using Microsoft.Extensions.Logging; -using Microsoft.Extensions.Options; -using NBitcoin; - -namespace BTCPayServer.Plugins.FixedFloat -{ - public class BreezSettings - { - public string InviteCode { get; set; } - public string Mnemonic { get; set; } - public string ApiKey { get; set; } - } - - public class BreezService:IHostedService - { - private readonly StoreRepository _storeRepository; - private readonly IOptions _dataDirectories; - private readonly BTCPayNetworkProvider _btcPayNetworkProvider; - private readonly ILogger _logger; - private Dictionary _settings; - private Dictionary _clients = new(); - - public BreezService(StoreRepository storeRepository, - IOptions dataDirectories, - BTCPayNetworkProvider btcPayNetworkProvider, - ILogger logger) - { - _storeRepository = storeRepository; - _dataDirectories = dataDirectories; - _btcPayNetworkProvider = btcPayNetworkProvider; - _logger = logger; - } - - private string GetWorkDir() - { - var dir = _dataDirectories.Value.DataDir; - return Path.Combine(dir, "Plugins", "Breez"); - } - - TaskCompletionSource tcs = new(); - public async Task StartAsync(CancellationToken cancellationToken) - { - _settings = (await _storeRepository.GetSettingsAsync("Breez")).Where(pair => pair.Value is not null).ToDictionary(pair => pair.Key, pair => pair.Value!); - tcs.TrySetResult(); - } - - public async Task Get(string storeId) - { - await tcs.Task; - _settings.TryGetValue(storeId, out var settings); - return settings; - } - - public async Task Handle(string? storeId, BreezSettings? settings) - { - if (settings is null) - { - if (storeId is not null && _clients.Remove(storeId, out var client)) - { - client.Dispose(); - } - } - else - { - try - { - var client = new BreezLightningClient(settings.InviteCode, settings.ApiKey, GetWorkDir(), - _btcPayNetworkProvider.BTC.NBitcoinNetwork, settings.Mnemonic); - if (storeId is not null) - { - _clients.AddOrReplace(storeId, client); - } - return client; - } - catch (Exception e) - { - _logger.LogError(e, "Could not create Breez client"); - throw; - } - } - - return null; - } - - public async Task Set(string storeId, BreezSettings? settings) - { - - var result = await Handle(storeId, settings); - await _storeRepository.UpdateSetting(storeId, "Breez", settings!); - if (settings is null) - { - _settings.Remove(storeId); - - } - else if(result is not null ) - { - _settings.AddOrReplace(storeId, settings); - } - - - } - - public async Task StopAsync(CancellationToken cancellationToken) - { - _clients.Values.ToList().ForEach(c => c.Dispose()); - } - - public BreezLightningClient? GetClient(string storeId) - { - _clients.TryGetValue(storeId, out var client); - return client; - } - } - - public class BreezPlugin : BaseBTCPayServerPlugin - { - public override IBTCPayServerPlugin.PluginDependency[] Dependencies { get; } = - { - new() {Identifier = nameof(BTCPayServer), Condition = ">=1.12.0"} - }; - - public override void Execute(IServiceCollection applicationBuilder) - { - applicationBuilder.AddSingleton(); - applicationBuilder.AddSingleton(provider => provider.GetRequiredService()); - applicationBuilder.AddSingleton(); - applicationBuilder.AddSingleton(provider => provider.GetRequiredService()); - applicationBuilder.AddSingleton(new UIExtension("Breez/BreezNav", - "store-integrations-nav")); - base.Execute(applicationBuilder); - } - } -} \ No newline at end of file diff --git a/Plugins/BTCPayServer.Plugins.Breez/Views/Breez/Index.cshtml b/Plugins/BTCPayServer.Plugins.Breez/Views/Breez/Index.cshtml index 43200fe..45d6102 100644 --- a/Plugins/BTCPayServer.Plugins.Breez/Views/Breez/Index.cshtml +++ b/Plugins/BTCPayServer.Plugins.Breez/Views/Breez/Index.cshtml @@ -1,7 +1,7 @@ @using BTCPayServer @using BTCPayServer.Abstractions.Extensions -@using BTCPayServer.Plugins.FixedFloat -@model BreezSettings? +@using BTCPayServer.Plugins.Breez +@model BTCPayServer.Plugins.Breez.BreezSettings? @inject BreezService BreezService @{ ViewData.SetActivePage("Breez", "Breez", "Breez"); diff --git a/Plugins/BTCPayServer.Plugins.Breez/Views/Shared/Breez/LNPaymentMethodSetupTab.cshtml b/Plugins/BTCPayServer.Plugins.Breez/Views/Shared/Breez/LNPaymentMethodSetupTab.cshtml new file mode 100644 index 0000000..4ea9267 --- /dev/null +++ b/Plugins/BTCPayServer.Plugins.Breez/Views/Shared/Breez/LNPaymentMethodSetupTab.cshtml @@ -0,0 +1,74 @@ + +@inject BreezService BreezService; +@using BTCPayServer.Plugins.Breez +@model BTCPayServer.Models.StoreViewModels.LightningNodeViewModel +@{ + var storeId = Model.StoreId; + if(Model.CryptoCode != "BTC") + { + return; + } + var client = BreezService.GetClient(storeId); +} + +
+ @if (client is not null) + { + + } + else + { + Breez needs to be configured beforehand. + } +
+ + + diff --git a/Plugins/BTCPayServer.Plugins.Breez/Views/Shared/Breez/LNPaymentMethodSetupTabhead.cshtml b/Plugins/BTCPayServer.Plugins.Breez/Views/Shared/Breez/LNPaymentMethodSetupTabhead.cshtml new file mode 100644 index 0000000..87074cf --- /dev/null +++ b/Plugins/BTCPayServer.Plugins.Breez/Views/Shared/Breez/LNPaymentMethodSetupTabhead.cshtml @@ -0,0 +1,13 @@ +@inject BreezService BreezService; +@using BTCPayServer.Plugins.Breez +@model BTCPayServer.Models.StoreViewModels.LightningNodeViewModel + +@if (Model.CryptoCode != "BTC") +{ + return; +} +@{ + var client = BreezService.GetClient(Model.StoreId); +} + + \ No newline at end of file