Update Peers Whitelist

Update Peers Whitelist
cln-peer-swap
ShahanaFarooqui 2 years ago
parent a908ef2a52
commit 445cc4cd31

@ -100,7 +100,7 @@ export const allowSwapRequests = (req, res, next) => {
if (options.error) {
return res.status(options.statusCode).json({ message: options.message, error: options.error });
}
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/allowSwapRequests' + req.params.isAllowed;
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/allowSwapRequests/' + req.params.isAllowed;
request(options).then((body) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Swap Request Allowed/Not Allowed', data: body });
res.status(200).json(body);
@ -115,7 +115,7 @@ export const addSwapPeer = (req, res, next) => {
if (options.error) {
return res.status(options.statusCode).json({ message: options.message, error: options.error });
}
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/addPeer' + req.params.pubkey;
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/addPeer/' + req.params.pubkey;
request(options).then((body) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Swap Peer Added', data: body });
res.status(200).json(body);
@ -130,7 +130,7 @@ export const removeSwapPeer = (req, res, next) => {
if (options.error) {
return res.status(options.statusCode).json({ message: options.message, error: options.error });
}
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/removePeer' + req.params.pubkey;
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/removePeer/' + req.params.pubkey;
request(options).then((body) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Swap Peer Removed', data: body });
res.status(200).json(body);
@ -145,7 +145,7 @@ export const resendMessage = (req, res, next) => {
if (options.error) {
return res.status(options.statusCode).json({ message: options.message, error: options.error });
}
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/resendMessage' + req.params.swapId;
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/resendMessage/' + req.params.swapId;
request(options).then((body) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Message Resent', data: body });
res.status(200).json(body);

File diff suppressed because one or more lines are too long

@ -10,9 +10,9 @@
<link i18n-rel="" rel="mask-icon" href="assets/images/favicon-light/safari-pinned-tab.svg" color="#5bbad5">
<meta i18n-content="" name="msapplication-TileColor" content="#da532c">
<meta i18n-content="" name="theme-color" content="#ffffff">
<style>@font-face{font-family:Roboto;src:url(Roboto-Thin.f7a95c9c5999532c.woff2) format("woff2"),url(Roboto-Thin.c13c157cb81e8ebb.woff) format("woff");font-weight:100;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-ThinItalic.b0e084abf689f393.woff2) format("woff2"),url(Roboto-ThinItalic.1111028df6cea564.woff) format("woff");font-weight:100;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Light.0e01b6cd13b3857f.woff2) format("woff2"),url(Roboto-Light.603ca9a537b88428.woff) format("woff");font-weight:300;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-LightItalic.232ef4b20215f720.woff2) format("woff2"),url(Roboto-LightItalic.1b5e142f787151c8.woff) format("woff");font-weight:300;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Regular.475ba9e4e2d63456.woff2) format("woff2"),url(Roboto-Regular.bcefbfee882bc1cb.woff) format("woff");font-weight:400;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-RegularItalic.e3a9ebdaac06bbc4.woff2) format("woff2"),url(Roboto-RegularItalic.0668fae6af0cf8c2.woff) format("woff");font-weight:400;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Medium.457532032ceb0168.woff2) format("woff2"),url(Roboto-Medium.6e1ae5f0b324a0aa.woff) format("woff");font-weight:500;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-MediumItalic.872f7060602d55d2.woff2) format("woff2"),url(Roboto-MediumItalic.e06fb533801cbb08.woff) format("woff");font-weight:500;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Bold.447291a88c067396.woff2) format("woff2"),url(Roboto-Bold.fc482e6133cf5e26.woff) format("woff");font-weight:700;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-BoldItalic.1b15168ef6fa4e16.woff2) format("woff2"),url(Roboto-BoldItalic.e26ba339b06f09f7.woff) format("woff");font-weight:700;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Black.2eaa390d458c877d.woff2) format("woff2"),url(Roboto-Black.b25f67ad8583da68.woff) format("woff");font-weight:900;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-BlackItalic.7dc03ee444552bc5.woff2) format("woff2"),url(Roboto-BlackItalic.c8dc642467cb3099.woff) format("woff");font-weight:900;font-style:italic}html{width:100%;height:99%;line-height:1.5;overflow-x:hidden;font-family:Roboto,sans-serif!important;font-size:62.5%}body{box-sizing:border-box;height:100%;margin:0;overflow:hidden}*{margin:0;padding:0}</style><link rel="stylesheet" href="styles.43515fc39338348b.css" media="print" onload="this.media='all'"><noscript><link rel="stylesheet" href="styles.43515fc39338348b.css"></noscript></head>
<style>@font-face{font-family:Roboto;src:url(Roboto-Thin.f7a95c9c5999532c.woff2) format("woff2"),url(Roboto-Thin.c13c157cb81e8ebb.woff) format("woff");font-weight:100;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-ThinItalic.b0e084abf689f393.woff2) format("woff2"),url(Roboto-ThinItalic.1111028df6cea564.woff) format("woff");font-weight:100;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Light.0e01b6cd13b3857f.woff2) format("woff2"),url(Roboto-Light.603ca9a537b88428.woff) format("woff");font-weight:300;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-LightItalic.232ef4b20215f720.woff2) format("woff2"),url(Roboto-LightItalic.1b5e142f787151c8.woff) format("woff");font-weight:300;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Regular.475ba9e4e2d63456.woff2) format("woff2"),url(Roboto-Regular.bcefbfee882bc1cb.woff) format("woff");font-weight:400;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-RegularItalic.e3a9ebdaac06bbc4.woff2) format("woff2"),url(Roboto-RegularItalic.0668fae6af0cf8c2.woff) format("woff");font-weight:400;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Medium.457532032ceb0168.woff2) format("woff2"),url(Roboto-Medium.6e1ae5f0b324a0aa.woff) format("woff");font-weight:500;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-MediumItalic.872f7060602d55d2.woff2) format("woff2"),url(Roboto-MediumItalic.e06fb533801cbb08.woff) format("woff");font-weight:500;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Bold.447291a88c067396.woff2) format("woff2"),url(Roboto-Bold.fc482e6133cf5e26.woff) format("woff");font-weight:700;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-BoldItalic.1b15168ef6fa4e16.woff2) format("woff2"),url(Roboto-BoldItalic.e26ba339b06f09f7.woff) format("woff");font-weight:700;font-style:italic}@font-face{font-family:Roboto;src:url(Roboto-Black.2eaa390d458c877d.woff2) format("woff2"),url(Roboto-Black.b25f67ad8583da68.woff) format("woff");font-weight:900;font-style:normal}@font-face{font-family:Roboto;src:url(Roboto-BlackItalic.7dc03ee444552bc5.woff2) format("woff2"),url(Roboto-BlackItalic.c8dc642467cb3099.woff) format("woff");font-weight:900;font-style:italic}html{width:100%;height:99%;line-height:1.5;overflow-x:hidden;font-family:Roboto,sans-serif!important;font-size:62.5%}body{box-sizing:border-box;height:100%;margin:0;overflow:hidden}*{margin:0;padding:0}</style><link rel="stylesheet" href="styles.b8a4cc0e3dcfa6f3.css" media="print" onload="this.media='all'"><noscript><link rel="stylesheet" href="styles.b8a4cc0e3dcfa6f3.css"></noscript></head>
<body>
<rtl-app></rtl-app>
<script src="runtime.4b216667d6a60356.js" type="module"></script><script src="polyfills.eddc63f1737a019a.js" type="module"></script><script src="main.31d6322513f9b4d7.js" type="module"></script>
<script src="runtime.6242e8cc52d30154.js" type="module"></script><script src="polyfills.eddc63f1737a019a.js" type="module"></script><script src="main.0d408a12943660a3.js" type="module"></script>
</body></html>

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

@ -1 +1 @@
(()=>{"use strict";var e,v={},g={};function r(e){var n=g[e];if(void 0!==n)return n.exports;var t=g[e]={id:e,loaded:!1,exports:{}};return v[e].call(t.exports,t,t.exports,r),t.loaded=!0,t.exports}r.m=v,e=[],r.O=(n,t,f,o)=>{if(!t){var a=1/0;for(i=0;i<e.length;i++){for(var[t,f,o]=e[i],s=!0,u=0;u<t.length;u++)(!1&o||a>=o)&&Object.keys(r.O).every(b=>r.O[b](t[u]))?t.splice(u--,1):(s=!1,o<a&&(a=o));if(s){e.splice(i--,1);var d=f();void 0!==d&&(n=d)}}return n}o=o||0;for(var i=e.length;i>0&&e[i-1][2]>o;i--)e[i]=e[i-1];e[i]=[t,f,o]},r.n=e=>{var n=e&&e.__esModule?()=>e.default:()=>e;return r.d(n,{a:n}),n},r.d=(e,n)=>{for(var t in n)r.o(n,t)&&!r.o(e,t)&&Object.defineProperty(e,t,{enumerable:!0,get:n[t]})},r.f={},r.e=e=>Promise.all(Object.keys(r.f).reduce((n,t)=>(r.f[t](e,n),n),[])),r.u=e=>e+"."+{258:"525782ba4bbc257e",508:"06f7dec065381b97",515:"73bff63b24de0558",706:"911e43a7ac305c95"}[e]+".js",r.miniCssF=e=>{},r.o=(e,n)=>Object.prototype.hasOwnProperty.call(e,n),(()=>{var e={},n="RTLApp:";r.l=(t,f,o,i)=>{if(e[t])e[t].push(f);else{var a,s;if(void 0!==o)for(var u=document.getElementsByTagName("script"),d=0;d<u.length;d++){var l=u[d];if(l.getAttribute("src")==t||l.getAttribute("data-webpack")==n+o){a=l;break}}a||(s=!0,(a=document.createElement("script")).type="module",a.charset="utf-8",a.timeout=120,r.nc&&a.setAttribute("nonce",r.nc),a.setAttribute("data-webpack",n+o),a.src=r.tu(t)),e[t]=[f];var c=(m,b)=>{a.onerror=a.onload=null,clearTimeout(p);var h=e[t];if(delete e[t],a.parentNode&&a.parentNode.removeChild(a),h&&h.forEach(_=>_(b)),m)return m(b)},p=setTimeout(c.bind(null,void 0,{type:"timeout",target:a}),12e4);a.onerror=c.bind(null,a.onerror),a.onload=c.bind(null,a.onload),s&&document.head.appendChild(a)}}})(),r.r=e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},r.nmd=e=>(e.paths=[],e.children||(e.children=[]),e),(()=>{var e;r.tt=()=>(void 0===e&&(e={createScriptURL:n=>n},"undefined"!=typeof trustedTypes&&trustedTypes.createPolicy&&(e=trustedTypes.createPolicy("angular#bundler",e))),e)})(),r.tu=e=>r.tt().createScriptURL(e),r.p="",(()=>{var e={666:0};r.f.j=(f,o)=>{var i=r.o(e,f)?e[f]:void 0;if(0!==i)if(i)o.push(i[2]);else if(666!=f){var a=new Promise((l,c)=>i=e[f]=[l,c]);o.push(i[2]=a);var s=r.p+r.u(f),u=new Error;r.l(s,l=>{if(r.o(e,f)&&(0!==(i=e[f])&&(e[f]=void 0),i)){var c=l&&("load"===l.type?"missing":l.type),p=l&&l.target&&l.target.src;u.message="Loading chunk "+f+" failed.\n("+c+": "+p+")",u.name="ChunkLoadError",u.type=c,u.request=p,i[1](u)}},"chunk-"+f,f)}else e[f]=0},r.O.j=f=>0===e[f];var n=(f,o)=>{var u,d,[i,a,s]=o,l=0;if(i.some(p=>0!==e[p])){for(u in a)r.o(a,u)&&(r.m[u]=a[u]);if(s)var c=s(r)}for(f&&f(o);l<i.length;l++)r.o(e,d=i[l])&&e[d]&&e[d][0](),e[d]=0;return r.O(c)},t=self.webpackChunkRTLApp=self.webpackChunkRTLApp||[];t.forEach(n.bind(null,0)),t.push=n.bind(null,t.push.bind(t))})()})();
(()=>{"use strict";var e,v={},g={};function r(e){var n=g[e];if(void 0!==n)return n.exports;var t=g[e]={id:e,loaded:!1,exports:{}};return v[e].call(t.exports,t,t.exports,r),t.loaded=!0,t.exports}r.m=v,e=[],r.O=(n,t,f,o)=>{if(!t){var a=1/0;for(i=0;i<e.length;i++){for(var[t,f,o]=e[i],s=!0,u=0;u<t.length;u++)(!1&o||a>=o)&&Object.keys(r.O).every(b=>r.O[b](t[u]))?t.splice(u--,1):(s=!1,o<a&&(a=o));if(s){e.splice(i--,1);var l=f();void 0!==l&&(n=l)}}return n}o=o||0;for(var i=e.length;i>0&&e[i-1][2]>o;i--)e[i]=e[i-1];e[i]=[t,f,o]},r.n=e=>{var n=e&&e.__esModule?()=>e.default:()=>e;return r.d(n,{a:n}),n},r.d=(e,n)=>{for(var t in n)r.o(n,t)&&!r.o(e,t)&&Object.defineProperty(e,t,{enumerable:!0,get:n[t]})},r.f={},r.e=e=>Promise.all(Object.keys(r.f).reduce((n,t)=>(r.f[t](e,n),n),[])),r.u=e=>e+"."+{258:"525782ba4bbc257e",508:"06f7dec065381b97",515:"73bff63b24de0558",706:"174f47f29c93805b"}[e]+".js",r.miniCssF=e=>{},r.o=(e,n)=>Object.prototype.hasOwnProperty.call(e,n),(()=>{var e={},n="RTLApp:";r.l=(t,f,o,i)=>{if(e[t])e[t].push(f);else{var a,s;if(void 0!==o)for(var u=document.getElementsByTagName("script"),l=0;l<u.length;l++){var d=u[l];if(d.getAttribute("src")==t||d.getAttribute("data-webpack")==n+o){a=d;break}}a||(s=!0,(a=document.createElement("script")).type="module",a.charset="utf-8",a.timeout=120,r.nc&&a.setAttribute("nonce",r.nc),a.setAttribute("data-webpack",n+o),a.src=r.tu(t)),e[t]=[f];var c=(m,b)=>{a.onerror=a.onload=null,clearTimeout(p);var h=e[t];if(delete e[t],a.parentNode&&a.parentNode.removeChild(a),h&&h.forEach(_=>_(b)),m)return m(b)},p=setTimeout(c.bind(null,void 0,{type:"timeout",target:a}),12e4);a.onerror=c.bind(null,a.onerror),a.onload=c.bind(null,a.onload),s&&document.head.appendChild(a)}}})(),r.r=e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},r.nmd=e=>(e.paths=[],e.children||(e.children=[]),e),(()=>{var e;r.tt=()=>(void 0===e&&(e={createScriptURL:n=>n},"undefined"!=typeof trustedTypes&&trustedTypes.createPolicy&&(e=trustedTypes.createPolicy("angular#bundler",e))),e)})(),r.tu=e=>r.tt().createScriptURL(e),r.p="",(()=>{var e={666:0};r.f.j=(f,o)=>{var i=r.o(e,f)?e[f]:void 0;if(0!==i)if(i)o.push(i[2]);else if(666!=f){var a=new Promise((d,c)=>i=e[f]=[d,c]);o.push(i[2]=a);var s=r.p+r.u(f),u=new Error;r.l(s,d=>{if(r.o(e,f)&&(0!==(i=e[f])&&(e[f]=void 0),i)){var c=d&&("load"===d.type?"missing":d.type),p=d&&d.target&&d.target.src;u.message="Loading chunk "+f+" failed.\n("+c+": "+p+")",u.name="ChunkLoadError",u.type=c,u.request=p,i[1](u)}},"chunk-"+f,f)}else e[f]=0},r.O.j=f=>0===e[f];var n=(f,o)=>{var u,l,[i,a,s]=o,d=0;if(i.some(p=>0!==e[p])){for(u in a)r.o(a,u)&&(r.m[u]=a[u]);if(s)var c=s(r)}for(f&&f(o);d<i.length;d++)r.o(e,l=i[d])&&e[l]&&e[l][0](),e[l]=0;return r.O(c)},t=self.webpackChunkRTLApp=self.webpackChunkRTLApp||[];t.forEach(n.bind(null,0)),t.push=n.bind(null,t.push.bind(t))})()})();

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

@ -93,7 +93,7 @@ export const allowSwapRequests = (req, res, next) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Allowing/Not Allowing Swap Requests..' });
options = common.getOptions(req);
if (options.error) { return res.status(options.statusCode).json({ message: options.message, error: options.error }); }
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/allowSwapRequests' + req.params.isAllowed;
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/allowSwapRequests/' + req.params.isAllowed;
request(options).then((body) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Swap Request Allowed/Not Allowed', data: body });
res.status(200).json(body);
@ -107,7 +107,7 @@ export const addSwapPeer = (req, res, next) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Adding Swap Peer..' });
options = common.getOptions(req);
if (options.error) { return res.status(options.statusCode).json({ message: options.message, error: options.error }); }
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/addPeer' + req.params.pubkey;
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/addPeer/' + req.params.pubkey;
request(options).then((body) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Swap Peer Added', data: body });
res.status(200).json(body);
@ -121,7 +121,7 @@ export const removeSwapPeer = (req, res, next) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Removing Swap Peer..' });
options = common.getOptions(req);
if (options.error) { return res.status(options.statusCode).json({ message: options.message, error: options.error }); }
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/removePeer' + req.params.pubkey;
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/removePeer/' + req.params.pubkey;
request(options).then((body) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Swap Peer Removed', data: body });
res.status(200).json(body);
@ -135,7 +135,7 @@ export const resendMessage = (req, res, next) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Resending Message..' });
options = common.getOptions(req);
if (options.error) { return res.status(options.statusCode).json({ message: options.message, error: options.error }); }
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/resendMessage' + req.params.swapId;
options.url = req.session.selectedNode.ln_server_url + '/v1/peerswap/resendMessage/' + req.params.swapId;
request(options).then((body) => {
logger.log({ selectedNode: req.session.selectedNode, level: 'INFO', fileName: 'Peerswap', msg: 'Message Resent', data: body });
res.status(200).json(body);

@ -37,11 +37,10 @@ export const routes: Routes = [
{ path: '', pathMatch: 'full', redirectTo: 'layout' },
{ path: 'layout', component: NodeSettingsComponent, canActivate: [AuthGuard] },
{
path: 'services', component: ServicesSettingsComponent, canActivate: [AuthGuard], children: [
{ path: '', pathMatch: 'full', redirectTo: 'loop' },
path: 'serviceconf', component: ServicesSettingsComponent, canActivate: [AuthGuard], children: [
{ path: 'loop', component: LoopServiceSettingsComponent, canActivate: [AuthGuard] },
{ path: 'boltz', component: BoltzServiceSettingsComponent, canActivate: [AuthGuard] },
{ path: 'peerswap', component: PeerswapServiceSettingsComponent, canActivate: [AuthGuard] }
{ path: 'prswp', component: PeerswapServiceSettingsComponent, canActivate: [AuthGuard] }
]
},
{ path: 'experimental', component: ExperimentalSettingsComponent, canActivate: [AuthGuard] },

@ -4,7 +4,7 @@
<div fxFlex="95" fxLayoutAlign="start start">
<span class="page-title">Initiate a Swapin</span>
</div>
<button tabindex="5" fxFlex="5" fxLayoutAlign="center" class="btn-close-x p-0" [mat-dialog-close]="false" default
<button tabindex="6" fxFlex="5" fxLayoutAlign="center" class="btn-close-x p-0" [mat-dialog-close]="false" default
mat-button>X</button>
</mat-card-header>
<mat-card-content class="padding-gap-x-large">
@ -13,7 +13,7 @@
<mat-form-field fxFlex="100" fxLayoutAlign="start end">
<input matInput [value]="sPeer.short_channel_id" placeholder="Short Channel ID" tabindex="1" name="shortChanId" disabled>
</mat-form-field>
<mat-form-field fxFlex="100">
<mat-form-field *ngIf="sPeer.remote_balance >= 100000" fxFlex="100">
<input matInput autoFocus [(ngModel)]="swapAmount" (keyup)="onAmountChange()" placeholder="Amount"
type="number" [step]="1000" [min]="100000" [max]="sPeer.remote_balance" tabindex="2" name="swapAmt" #swapAmt="ngModel" required>
<span matSuffix class="ml-1"> Sats </span>
@ -26,10 +26,14 @@
<fa-icon [icon]="faExclamationTriangle" class="mr-1 alert-icon"></fa-icon>
<span *ngIf="swapInError !== ''">{{swapInError}}</span>
</div>
<div fxFlex="100" class="alert alert-danger mt-2" *ngIf="sPeer.remote_balance < 100000">
<fa-icon [icon]="faExclamationTriangle" class="mr-1 alert-icon"></fa-icon>
<span>Insufficient remote balance for swap in.</span>
</div>
<div fxLayout="row" fxFlex="100" class="mt-1" fxLayoutAlign="end center">
<button class="mr-1" mat-button color="primary" tabindex="3" type="button" (click)="resetData()">Clear
Field</button>
<button mat-button color="primary" (click)="onExecuteSwapin()" tabindex="4">Execute</button>
<button class="mr-1" mat-button color="primary" tabindex="3" type="button" (click)="resetData()" [disabled]="sPeer.remote_balance < 100000">Clear Field</button>
<button mat-button color="primary" (click)="goToSwapCanceled()" tabindex="4" *ngIf="flgswapCanceled">Go to Swap Canceled</button>
<button mat-button color="primary" (click)="onExecuteSwapin()" tabindex="5" *ngIf="!flgswapCanceled" [disabled]="sPeer.remote_balance < 100000">{{swapInError !== '' ? 'Retry' : 'Execute'}}</button>
</div>
</form>
</mat-card-content>

@ -1,5 +1,6 @@
import { waitForAsync, ComponentFixture, TestBed } from '@angular/core/testing';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
import { RouterTestingModule } from '@angular/router/testing';
import { StoreModule } from '@ngrx/store';
import { EffectsModule } from '@ngrx/effects';
import { MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';
@ -24,6 +25,7 @@ describe('CLNSwapInModalComponent', () => {
declarations: [CLNSwapInModalComponent],
imports: [
BrowserAnimationsModule,
RouterTestingModule,
SharedModule,
StoreModule.forRoot({ root: RootReducer, lnd: LNDReducer, cln: CLNReducer, ecl: ECLReducer }),
EffectsModule.forRoot([mockRTLEffects, mockLNDEffects, mockCLEffects, mockECLEffects])

@ -15,7 +15,8 @@ import { CommonService } from '../../../../shared/services/common.service';
import { RTLState } from '../../../../store/rtl.state';
import { SelNodeChild } from '../../../../shared/models/RTLconfig';
import { clnNodeSettings } from '../../../store/cln.selector';
import { swapIn } from '../../../store/cln.actions';
import { fetchSwaps, swapIn } from '../../../store/cln.actions';
import { Router } from '@angular/router';
@Component({
selector: 'rtl-swap-in-modal',
@ -30,9 +31,10 @@ export class CLNSwapInModalComponent implements OnInit, OnDestroy {
public swapAmount: number | null;
public swapAmountHint = '';
public swapInError = '';
public flgswapCanceled = false;
private unSubs: Array<Subject<void>> = [new Subject(), new Subject(), new Subject(), new Subject(), new Subject()];
constructor(public dialogRef: MatDialogRef<CLNSwapInModalComponent>, @Inject(MAT_DIALOG_DATA) public data: CLNSwapInformation, private store: Store<RTLState>, private decimalPipe: DecimalPipe, private commonService: CommonService, private actions: Actions) { }
constructor(public dialogRef: MatDialogRef<CLNSwapInModalComponent>, @Inject(MAT_DIALOG_DATA) public data: CLNSwapInformation, private store: Store<RTLState>, private decimalPipe: DecimalPipe, private commonService: CommonService, private actions: Actions, private router: Router) { }
ngOnInit() {
this.sPeer = this.data.swapPeer;
@ -46,6 +48,9 @@ export class CLNSwapInModalComponent implements OnInit, OnDestroy {
if (action.type === CLNActions.UPDATE_API_CALL_STATUS_CLN && action.payload.action === 'PeerswapSwapin') {
if (action.payload.status === APICallStatusEnum.ERROR) {
this.swapInError = action.payload.message;
if (this.swapInError.includes('Peerswap-listswaps')) {
this.flgswapCanceled = true;
}
}
if (action.payload.status === APICallStatusEnum.COMPLETED) {
this.dialogRef.close();
@ -54,8 +59,15 @@ export class CLNSwapInModalComponent implements OnInit, OnDestroy {
});
}
goToSwapCanceled() {
this.store.dispatch(fetchSwaps());
this.router.navigate(['./cln/services/peerswap/pscanceled']);
this.dialogRef.close();
}
onExecuteSwapin(): boolean | void {
this.swapInError = '';
this.flgswapCanceled = false;
if (!this.swapAmount || !this.sPeer || !this.sPeer.short_channel_id) { return true; }
this.store.dispatch(swapIn({ payload: { alias: this.sPeer.alias || '', amountSats: this.swapAmount, shortChannelId: this.sPeer?.short_channel_id, asset: 'btc' } }));
}
@ -64,6 +76,7 @@ export class CLNSwapInModalComponent implements OnInit, OnDestroy {
this.swapAmount = null;
this.swapAmountHint = '';
this.swapInError = '';
this.flgswapCanceled = false;
}
onAmountChange() {

@ -4,7 +4,7 @@
<div fxFlex="95" fxLayoutAlign="start start">
<span class="page-title">Initiate a Swapout</span>
</div>
<button tabindex="5" fxFlex="5" fxLayoutAlign="center" class="btn-close-x p-0" [mat-dialog-close]="false" default
<button tabindex="6" fxFlex="5" fxLayoutAlign="center" class="btn-close-x p-0" [mat-dialog-close]="false" default
mat-button>X</button>
</mat-card-header>
<mat-card-content class="padding-gap-x-large">
@ -13,7 +13,7 @@
<mat-form-field fxFlex="100" fxLayoutAlign="start end">
<input matInput [value]="sPeer.short_channel_id" placeholder="Short Channel ID" tabindex="1" name="shortChanId" disabled>
</mat-form-field>
<mat-form-field fxFlex="100">
<mat-form-field *ngIf="sPeer.local_balance >= 100000" fxFlex="100">
<input matInput autoFocus [(ngModel)]="swapAmount" (keyup)="onAmountChange()" placeholder="Amount"
type="number" [step]="1000" [min]="100000" [max]="sPeer.local_balance" tabindex="2" name="swapAmt" #swapAmt="ngModel" required>
<span matSuffix class="ml-1"> Sats </span>
@ -26,10 +26,14 @@
<fa-icon [icon]="faExclamationTriangle" class="mr-1 alert-icon"></fa-icon>
<span *ngIf="swapOutError !== ''">{{swapOutError}}</span>
</div>
<div fxFlex="100" class="alert alert-danger mt-2" *ngIf="sPeer.local_balance < 100000">
<fa-icon [icon]="faExclamationTriangle" class="mr-1 alert-icon"></fa-icon>
<span>Insufficient local balance for swap out.</span>
</div>
<div fxLayout="row" fxFlex="100" class="mt-1" fxLayoutAlign="end center">
<button class="mr-1" mat-button color="primary" tabindex="3" type="button" (click)="resetData()">Clear
Field</button>
<button mat-button color="primary" (click)="onExecuteSwapout()" tabindex="4">Execute</button>
<button class="mr-1" mat-button color="primary" tabindex="3" type="button" (click)="resetData()" [disabled]="sPeer.local_balance < 100000">Clear Field</button>
<button mat-button color="primary" (click)="goToSwapCanceled()" tabindex="4" *ngIf="flgswapCanceled">Go to Swap Canceled</button>
<button mat-button color="primary" (click)="onExecuteSwapout()" tabindex="5" *ngIf="!flgswapCanceled" [disabled]="sPeer.local_balance < 100000">{{swapOutError !== '' ? 'Retry' : 'Execute'}}</button>
</div>
</form>
</mat-card-content>

@ -1,5 +1,6 @@
import { waitForAsync, ComponentFixture, TestBed } from '@angular/core/testing';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
import { RouterTestingModule } from '@angular/router/testing';
import { StoreModule } from '@ngrx/store';
import { EffectsModule } from '@ngrx/effects';
import { MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';
@ -25,6 +26,7 @@ describe('CLNSwapOutModalComponent', () => {
imports: [
BrowserAnimationsModule,
SharedModule,
RouterTestingModule,
StoreModule.forRoot({ root: RootReducer, lnd: LNDReducer, cln: CLNReducer, ecl: ECLReducer }),
EffectsModule.forRoot([mockRTLEffects, mockLNDEffects, mockCLEffects, mockECLEffects])
],

@ -15,7 +15,8 @@ import { CommonService } from '../../../../shared/services/common.service';
import { RTLState } from '../../../../store/rtl.state';
import { SelNodeChild } from '../../../../shared/models/RTLconfig';
import { clnNodeSettings } from '../../../store/cln.selector';
import { swapOut } from '../../../store/cln.actions';
import { fetchSwaps, swapOut } from '../../../store/cln.actions';
import { Router } from '@angular/router';
@Component({
selector: 'rtl-swap-out-modal',
@ -30,9 +31,10 @@ export class CLNSwapOutModalComponent implements OnInit, OnDestroy {
public swapAmount: number | null;
public swapAmountHint = '';
public swapOutError = '';
public flgswapCanceled = false;
private unSubs: Array<Subject<void>> = [new Subject(), new Subject(), new Subject(), new Subject(), new Subject()];
constructor(public dialogRef: MatDialogRef<CLNSwapOutModalComponent>, @Inject(MAT_DIALOG_DATA) public data: CLNSwapInformation, private store: Store<RTLState>, private decimalPipe: DecimalPipe, private commonService: CommonService, private actions: Actions) { }
constructor(public dialogRef: MatDialogRef<CLNSwapOutModalComponent>, @Inject(MAT_DIALOG_DATA) public data: CLNSwapInformation, private store: Store<RTLState>, private decimalPipe: DecimalPipe, private commonService: CommonService, private actions: Actions, private router: Router) { }
ngOnInit() {
this.sPeer = this.data.swapPeer;
@ -46,6 +48,9 @@ export class CLNSwapOutModalComponent implements OnInit, OnDestroy {
if (action.type === CLNActions.UPDATE_API_CALL_STATUS_CLN && action.payload.action === 'PeerswapSwapout') {
if (action.payload.status === APICallStatusEnum.ERROR) {
this.swapOutError = action.payload.message;
if (this.swapOutError.includes('Peerswap-listswaps')) {
this.flgswapCanceled = true;
}
}
if (action.payload.status === APICallStatusEnum.COMPLETED) {
this.dialogRef.close();
@ -54,8 +59,15 @@ export class CLNSwapOutModalComponent implements OnInit, OnDestroy {
});
}
goToSwapCanceled() {
this.store.dispatch(fetchSwaps());
this.router.navigate(['./cln/services/peerswap/pscanceled']);
this.dialogRef.close();
}
onExecuteSwapout(): boolean | void {
this.swapOutError = '';
this.flgswapCanceled = false;
if (!this.swapAmount || !this.sPeer || !this.sPeer.short_channel_id) { return true; }
this.store.dispatch(swapOut({ payload: { alias: this.sPeer.alias || '', amountSats: this.swapAmount, shortChannelId: this.sPeer?.short_channel_id, asset: 'btc' } }));
}
@ -64,6 +76,7 @@ export class CLNSwapOutModalComponent implements OnInit, OnDestroy {
this.swapAmount = null;
this.swapAmountHint = '';
this.swapOutError = '';
this.flgswapCanceled = false;
}
onAmountChange() {

@ -947,6 +947,10 @@ export class CLNEffects implements OnDestroy {
pipe(map((swapRes: ActiveSwap) => {
this.logger.info(swapRes);
this.store.dispatch(updateCLAPICallStatus({ payload: { action: 'GetSwap', status: APICallStatusEnum.COMPLETED } }));
if (swapRes.current === 'State_ClaimedPreimage' || swapRes.current === 'State_ClaimedCoop') {
this.store.dispatch(fetchUTXOs());
this.store.dispatch(fetchBalance());
}
return {
type: CLNActions.UPDATE_SWAP_STATE_CLN,
payload: { swapId: action.payload, state: swapRes.current, type: swapRes.type === 1 ? SwapTypeEnum.SWAP_IN : SwapTypeEnum.SWAP_OUT }

@ -20,7 +20,7 @@ export class NodeConfigComponent implements OnInit, OnDestroy {
public showLnConfig = false;
public selNode: ConfigSettingsNode | any;
public lnImplementationStr = '';
public links = [{ link: 'layout', name: 'Layout' }, { link: 'services', name: 'Services' }, { link: 'experimental', name: 'Experimental' }, { link: 'lnconfig', name: this.lnImplementationStr }];
public links = [{ link: 'layout', name: 'Layout' }, { link: 'serviceconf', name: 'Services' }, { link: 'experimental', name: 'Experimental' }, { link: 'lnconfig', name: this.lnImplementationStr }];
public activeLink = '';
private unSubs: Array<Subject<void>> = [new Subject(), new Subject(), new Subject()];

@ -1,14 +1,66 @@
<div [perfectScrollbar] fxLayout="column" fxFlex="100">
<div fxLayout="column" fxFlex="100">
<div fxFlex="100" class="alert alert-info mt-1">
<fa-icon [icon]="faInfoCircle" class="mr-1 alert-icon"></fa-icon>
<span>Please ensure that <strong>peerswap</strong> plugin is running and accessible to RTL before enabling this service. Click <strong><a href="https://www.peerswap.dev/" target="_blank">here</a></strong> to learn more about peerswap.</span>
<span>Please ensure that <strong>peerswap plugin</strong> is running and accessible to RTL before enabling this service. Click <strong><a href="https://www.peerswap.dev/" target="_blank">here</a></strong> to learn more about peerswap.</span>
</div>
<form fxLayout="column" fxFlex="100" fxLayoutAlign="start stretch" class="settings-container page-sub-title-container mt-1" #form="ngForm">
<div fxLayout="column" fxFlex="50" fxLayoutAlign="start stretch">
<mat-slide-toggle autoFocus class="mb-1" tabindex="1" color="primary" [(ngModel)]="enablePeerswap" name="peerswap">Enable Peerswap Service</mat-slide-toggle>
<div fxLayout="column" fxFlex="100" fxLayoutAlign="start stretch" class="settings-container page-sub-title-container">
<mat-slide-toggle autoFocus class="my-2" tabindex="1" color="primary" [(ngModel)]="enablePeerswap" (change)="onUpdateService()" name="peerswap">Enable Peerswap Service</mat-slide-toggle>
<div *ngIf="enablePeerswap && reloadPolicyError !== ''" class="padding-gap-large error-border">
<div fxLayout="row">
<div fxFlex="100" class="alert alert-danger mt-1">
<fa-icon [icon]="faExclamationTriangle" class="mr-1 alert-icon"></fa-icon>
<span>{{reloadPolicyError}}</span>
</div>
</div>
</div>
</form>
<div fxLayout="row" class="mt-2">
<button mat-flat-button color="primary" type="submit" (click)="onUpdateService()" tabindex="5">Update</button>
</div>
<div *ngIf="enablePeerswap && reloadPolicyError === ''" class="padding-gap-large bordered-box">
<div fxLayout="row">
<div fxFlex="100">
<h4 fxLayoutAlign="start" class="font-bold-500">Accept All Peers</h4>
<span class="foreground-secondary-text">{{reloadPolicy?.AcceptAllPeers ? 'Yes' : 'No'}}</span>
</div>
</div>
<mat-divider [inset]="true" class="my-1"></mat-divider>
<div fxLayout="row">
<div fxFlex="100">
<h4 fxLayoutAlign="start" class="font-bold-500">Onchain Reserve (Sats)</h4>
<span class="foreground-secondary-text">{{reloadPolicy?.ReserveOnchainMsat / 1000 | number}}</span>
</div>
</div>
<mat-divider [inset]="true" class="my-1"></mat-divider>
<div fxLayout="row">
<div fxFlex="100">
<h4 fxLayoutAlign="start" class="font-bold-500">Update Peerswap Whitelist</h4>
<div *ngIf="addRemoveError !== ''" class="padding-gap error-border">
<div fxLayout="row">
<div fxFlex="100" class="alert alert-danger mt-1">
<fa-icon [icon]="faExclamationTriangle" class="mr-1 alert-icon"></fa-icon>
<span>{{addRemoveError}}</span>
</div>
</div>
</div>
<div>
<mat-card *ngFor="let allowedPeer of reloadPolicy?.PeerAllowlist" fxLayout="row" fxLayoutAlign="start center" class="mb-1 peer-card">
<div fxLayoutAlign="center center">
<button mat-icon-button color="primary" (click)="onRemovePeer(allowedPeer)" class="mr-1" matTooltip="Remove Peer" matTooltipPosition="below">
<mat-icon>remove_circle_outline</mat-icon>
</button>
</div>
<div fxLayoutAlign="start center" class="mt-5px">{{allowedPeer}}</div>
</mat-card>
<mat-card fxLayout="row" fxLayoutAlign="start center" class="mb-1 peer-card" >
<div fxLayoutAlign="center center" matTooltip="Add Peer" matTooltipPosition="below">
<button mat-icon-button color="primary" [disabled]="!addPeerNodeId || addPeerNodeId === '' || addPeerNodeId.length < 50" (click)="onAddPeer()" class="mr-1">
<mat-icon>add_circle_outline</mat-icon>
</button>
</div>
<mat-form-field fxLayoutAlign="start stretch" fxFlex="50" class="mt-5px">
<input matInput placeholder="Node Id" [(ngModel)]="addPeerNodeId" name="nodeId" tabindex="4">
</mat-form-field>
</mat-card>
</div>
</div>
</div>
</div>
</div>
</div>

@ -1,4 +1,4 @@
import { Component, ViewChild, OnInit, OnDestroy } from '@angular/core';
import { Component, OnInit, OnDestroy } from '@angular/core';
import { Subject } from 'rxjs';
import { takeUntil } from 'rxjs/operators';
import { Store } from '@ngrx/store';
@ -6,13 +6,16 @@ import { Store } from '@ngrx/store';
import { ServicesEnum, UI_MESSAGES } from '../../../../services/consts-enums-functions';
import { ConfigSettingsNode } from '../../../../models/RTLconfig';
import { LoggerService } from '../../../../services/logger.service';
import { faInfoCircle } from '@fortawesome/free-solid-svg-icons';
import { DataService } from '../../../../services/data.service';
import { faInfoCircle, faExclamationTriangle } from '@fortawesome/free-solid-svg-icons';
import { updateServiceSettings } from '../../../../../store/rtl.actions';
import { RTLState } from '../../../../../store/rtl.state';
import { setChildNodeSettingsLND } from '../../../../../lnd/store/lnd.actions';
import { setChildNodeSettingsCL } from '../../../../../cln/store/cln.actions';
import { setChildNodeSettingsECL } from '../../../../../eclair/store/ecl.actions';
import { rootSelectedNode } from '../../../../../store/rtl.selector';
import { PeerswapReloadPolicy } from '../../../../models/clnModels';
@Component({
selector: 'rtl-peerswap-service-settings',
@ -22,15 +25,30 @@ import { rootSelectedNode } from '../../../../../store/rtl.selector';
export class PeerswapServiceSettingsComponent implements OnInit, OnDestroy {
public faInfoCircle = faInfoCircle;
public faExclamationTriangle = faExclamationTriangle;
public selNode: ConfigSettingsNode | any;
public enablePeerswap = false;
unSubs: Array<Subject<void>> = [new Subject(), new Subject()];
public allowSwapRequests = false;
public reloadPolicy: PeerswapReloadPolicy | null = null;
public reloadPolicyError = '';
public addRemoveError = '';
public addPeerNodeId = '';
public unSubs: Array<Subject<void>> = [new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject()];
constructor(private logger: LoggerService, private store: Store<RTLState>) { }
constructor(private logger: LoggerService, private store: Store<RTLState>, private dataService: DataService) { }
ngOnInit() {
this.dataService.peerswapReloadPolicy().pipe(takeUntil(this.unSubs[0])).
subscribe({
next: (res) => {
this.reloadPolicy = res;
}, error: (err) => {
this.reloadPolicyError = 'ERROR: ' + err;
}
});
this.store.select(rootSelectedNode).
pipe(takeUntil(this.unSubs[0])).
pipe(takeUntil(this.unSubs[1])).
subscribe((selNode) => {
this.selNode = selNode;
this.enablePeerswap = !!selNode?.settings.enablePeerswap;
@ -60,6 +78,33 @@ export class PeerswapServiceSettingsComponent implements OnInit, OnDestroy {
}));
}
onAddPeer() {
this.addRemoveError = '';
this.dataService.addPeerToPeerswap(this.addPeerNodeId).pipe(takeUntil(this.unSubs[2])).
subscribe({
next: (res) => {
this.reloadPolicy = res;
this.addPeerNodeId = '';
}, error: (err) => {
this.addRemoveError = 'ERROR: ' + err;
setTimeout(() => { this.addRemoveError = ''; }, 3000);
}
});
}
onRemovePeer(peerNodeId: string) {
this.addRemoveError = '';
this.dataService.removePeerFromPeerswap(peerNodeId).pipe(takeUntil(this.unSubs[3])).
subscribe({
next: (res) => {
this.reloadPolicy = res;
}, error: (err) => {
this.addRemoveError = 'ERROR: ' + err;
setTimeout(() => { this.addRemoveError = ''; }, 3000);
}
});
}
ngOnDestroy() {
this.unSubs.forEach((unsub) => {
unsub.next();

@ -5,7 +5,7 @@
<div fxLayout="column" class="padding-gap-x">
<mat-card>
<mat-card-content fxLayout="column">
<nav mat-tab-nav-bar>
<nav mat-tab-nav-bar #navbar>
<div *ngIf="selNode?.lnImplementation?.toUpperCase() === 'LND'" role="tab" mat-tab-link class="mat-tab-label" [active]="activeLink === links[0].link" (click)="activeLink = links[0].link" routerLink="{{links[0].link}}">{{links[0].name}}</div>
<div *ngIf="selNode?.lnImplementation?.toUpperCase() === 'LND'" role="tab" mat-tab-link class="mat-tab-label" [active]="activeLink === links[1].link" (click)="activeLink = links[1].link" routerLink="{{links[1].link}}" [state]="{ initial: false }">{{links[1].name}}</div>
<div *ngIf="selNode?.lnImplementation?.toUpperCase() === 'CLN'" role="tab" mat-tab-link class="mat-tab-label" [active]="activeLink === links[2].link" (click)="activeLink = links[2].link" routerLink="{{links[2].link}}">{{links[2].name}}</div>

@ -1,7 +1,7 @@
import { Component, OnInit, OnDestroy } from '@angular/core';
import { Router, ResolveEnd, Event, ActivatedRoute } from '@angular/router';
import { Subject } from 'rxjs';
import { takeUntil, filter } from 'rxjs/operators';
import { takeUntil, filter, take } from 'rxjs/operators';
import { faLayerGroup } from '@fortawesome/free-solid-svg-icons';
import { ConfigSettingsNode } from '../../../models/RTLconfig';
import { Store } from '@ngrx/store';
@ -16,34 +16,40 @@ import { rootSelectedNode } from '../../../../store/rtl.selector';
export class ServicesSettingsComponent implements OnInit, OnDestroy {
public faLayerGroup = faLayerGroup;
public links = [{ link: 'loop', name: 'Loop' }, { link: 'boltz', name: 'Boltz' }, { link: 'peerswap', name: 'Peerswap' }];
public links = [{ link: 'loop', name: 'Loop' }, { link: 'boltz', name: 'Boltz' }, { link: 'prswp', name: 'Peerswap' }];
public activeLink = '';
public selNode: ConfigSettingsNode | any;
private unSubs: Array<Subject<void>> = [new Subject(), new Subject(), new Subject()];
constructor(private store: Store<RTLState>, private router: Router, private activatedRoute: ActivatedRoute) { }
constructor(private store: Store<RTLState>, private router: Router, private activatedRoute: ActivatedRoute) {}
ngOnInit() {
this.router.routeReuseStrategy.shouldReuseRoute = () => false;
this.router.onSameUrlNavigation = 'ignore';
const linkFound = this.links.find((link) => this.router.url.includes(link.link));
this.activeLink = linkFound ? linkFound.link : this.links[0].link;
if (linkFound) { this.activeLink = linkFound.link; }
this.router.events.pipe(takeUntil(this.unSubs[0]), filter((e) => e instanceof ResolveEnd)).
subscribe({
next: (value: ResolveEnd | Event) => {
const linkFound = this.links.find((link) => (<ResolveEnd>value).urlAfterRedirects.includes(link.link));
if (this.selNode.lnImplementation.toUpperCase() === 'CLN') {
this.activeLink = this.links[2].link;
} else {
this.activeLink = linkFound ? linkFound.link : this.links[0].link;
}
if (linkFound) { this.activeLink = linkFound.link; }
}
});
this.store.select(rootSelectedNode).pipe(takeUntil(this.unSubs[1])).subscribe((selNode) => {
this.selNode = selNode;
if (this.selNode.lnImplementation.toUpperCase() === 'CLN') {
this.activeLink = this.links[2].link;
this.router.navigate(['./' + this.activeLink], { relativeTo: this.activatedRoute });
} else if (this.selNode.lnImplementation.toUpperCase() === 'LND' && this.selNode.lnNode !== '') {
this.activeLink = this.links[0].link;
} else {
this.activeLink = '';
}
});
if (this.activeLink !== '') {
this.router.navigate(['./' + this.activeLink], { relativeTo: this.activatedRoute });
}
}
ngOnDestroy() {

@ -324,6 +324,10 @@ export const UI_MESSAGES = {
LIST_NETWORK_NODES: 'Getting Network Nodes List...',
PEERSWAP_SWAPOUT: 'Initializing Swapout...',
PEERSWAP_SWAPIN: 'Initializing Swapin...',
RELOAD_POLICY_PEERSWAP: 'Reload Peerswap Policy...',
ADD_PEER_PEERSWAP: 'Adding Peer To Peerswap Allowlist...',
REMOVE_PEER_PEERSWAP: 'Removing Peer From Peerswap Allowlist...',
UPDATE_ALLOW_SWAP_REQUESTS: 'Updating Swap Request Rule...',
LOG_OUT: 'Logging Out...'
};

@ -26,7 +26,8 @@ export class DataService implements OnDestroy {
private APIUrl = API_URL;
private lnImplementation = '';
public lnImplementationUpdated: BehaviorSubject<any> = new BehaviorSubject(null);
private unSubs: Array<Subject<void>> = [new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject()];
private unSubs: Array<Subject<void>> = [new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(), new Subject(),
new Subject(), new Subject(), new Subject(), new Subject(), new Subject()];
constructor(private httpClient: HttpClient, private store: Store<RTLState>, private logger: LoggerService, private snackBar: MatSnackBar, private titleCasePipe: TitleCasePipe) { }
@ -333,6 +334,70 @@ export class DataService implements OnDestroy {
}));
}
peerswapReloadPolicy() {
return this.lnImplementationUpdated.pipe(first((val) => val !== null), mergeMap((updatedLnImplementation) => {
this.store.dispatch(openSpinner({ payload: UI_MESSAGES.RELOAD_POLICY_PEERSWAP }));
return this.httpClient.get(this.APIUrl + '/' + updatedLnImplementation + environment.PEERSWAP_API + '/reloadPolicy').pipe(
takeUntil(this.unSubs[12]),
mergeMap((res) => {
this.store.dispatch(closeSpinner({ payload: UI_MESSAGES.RELOAD_POLICY_PEERSWAP }));
return of(res);
}), catchError((err) => {
this.handleErrorWithoutAlert('Reload Peerswap Policy', UI_MESSAGES.RELOAD_POLICY_PEERSWAP, err);
return throwError(() => this.extractErrorMessage(err));
})
);
}));
}
addPeerToPeerswap(peerNodeId: string) {
return this.lnImplementationUpdated.pipe(first((val) => val !== null), mergeMap((updatedLnImplementation) => {
this.store.dispatch(openSpinner({ payload: UI_MESSAGES.ADD_PEER_PEERSWAP }));
return this.httpClient.get(this.APIUrl + '/' + updatedLnImplementation + environment.PEERSWAP_API + '/addPeer/' + peerNodeId).pipe(
takeUntil(this.unSubs[13]),
mergeMap((res) => {
this.store.dispatch(closeSpinner({ payload: UI_MESSAGES.ADD_PEER_PEERSWAP }));
return of(res);
}), catchError((err) => {
this.handleErrorWithoutAlert('Add Peer To Peerswap', UI_MESSAGES.ADD_PEER_PEERSWAP, err);
return throwError(() => this.extractErrorMessage(err));
})
);
}));
}
removePeerFromPeerswap(peerNodeId: string) {
return this.lnImplementationUpdated.pipe(first((val) => val !== null), mergeMap((updatedLnImplementation) => {
this.store.dispatch(openSpinner({ payload: UI_MESSAGES.REMOVE_PEER_PEERSWAP }));
return this.httpClient.get(this.APIUrl + '/' + updatedLnImplementation + environment.PEERSWAP_API + '/removePeer/' + peerNodeId).pipe(
takeUntil(this.unSubs[14]),
mergeMap((res) => {
this.store.dispatch(closeSpinner({ payload: UI_MESSAGES.REMOVE_PEER_PEERSWAP }));
return of(res);
}), catchError((err) => {
this.handleErrorWithoutAlert('Remove Peer From Peerswap', UI_MESSAGES.REMOVE_PEER_PEERSWAP, err);
return throwError(() => this.extractErrorMessage(err));
})
);
}));
}
allowPeerswapRequests(flgAllow: boolean) {
return this.lnImplementationUpdated.pipe(first((val) => val !== null), mergeMap((updatedLnImplementation) => {
this.store.dispatch(openSpinner({ payload: UI_MESSAGES.UPDATE_ALLOW_SWAP_REQUESTS }));
return this.httpClient.get(this.APIUrl + '/' + updatedLnImplementation + environment.PEERSWAP_API + '/allowswaprequests/' + flgAllow).pipe(
takeUntil(this.unSubs[15]),
mergeMap((res) => {
this.store.dispatch(closeSpinner({ payload: UI_MESSAGES.UPDATE_ALLOW_SWAP_REQUESTS }));
return of(res);
}), catchError((err) => {
this.handleErrorWithoutAlert('Update Peerswap Request Rule', UI_MESSAGES.UPDATE_ALLOW_SWAP_REQUESTS, err);
return throwError(() => this.extractErrorMessage(err));
})
);
}));
}
mapAliases = (payload: any, storedChannels: ChannelCLN[]) => {
if (payload && payload.length > 0) {
payload.forEach((fhEvent, i) => {

@ -229,6 +229,15 @@
color: $foreground-text;
}
& .mat-form-field-appearance-legacy.mat-form-field.mat-focused {
& .mat-form-field-label {
color: $primary-darker;
}
& .mat-form-field-ripple {
background-color: $primary-darker;
}
}
& .mat-form-field-disabled {
& .mat-form-field-underline{
background-color: transparent;

@ -20,7 +20,7 @@ const initNodeAuthentication = { configPath: '', swapMacaroonPath: '', boltzMaca
export const initRootState: RootState = {
apiURL: '',
apisCallStatus: { Login: { status: APICallStatusEnum.UN_INITIATED }, IsAuthorized: { status: APICallStatusEnum.UN_INITIATED } },
selNode: { index: 1, lnNode: 'Node 1', settings: initNodeSettings, authentication: initNodeAuthentication, lnImplementation: 'LND' },
selNode: { index: 1, lnNode: '', settings: initNodeSettings, authentication: initNodeAuthentication, lnImplementation: 'LND' },
appConfig: {
defaultNodeIndex: -1,
selectedNodeIndex: -1,

Loading…
Cancel
Save