aboutsummaryrefslogtreecommitdiffstats
path: root/src/swap.js
diff options
context:
space:
mode:
authorAdam Soltys <[email protected]>2026-06-28 19:14:30 -0700
committerAdam Soltys <[email protected]>2026-06-28 19:14:30 -0700
commit93631253030839509551d7e1e6a995ed60e31b96 (patch)
treefa02596727bf3fb750cb5a88cbd04f63d54b19bb /src/swap.js
parent17f203ba3603c3f1ba9c8d14c53d9f10cccf3c81 (diff)
downloadcoinosv3-93631253030839509551d7e1e6a995ed60e31b96.tar.gz
coinosv3-93631253030839509551d7e1e6a995ed60e31b96.zip
Swaps: bound reverse amount by the provider's published limits, not a hardcoded 50k
doReverse rejected anything under a hardcoded 50,000 sats — which happens to be the regtest provider's minimum, but mainnet boltz's real minimum is 25,000 (and providers/networks differ), so valid 25k-50k mainnet swaps were refused and the max was unchecked client-side. Add SwapManager.reverseLimits() (GET /v2/swap/reverse, cached per API) and use it in the swap UI: show the real min/max range under the amount field and validate against it. Reset the cached limits when the network or provider changes. Verified: regtest min/max 50,000/40,294,967; mainnet 25,000/25,000,000. Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
Diffstat (limited to 'src/swap.js')
-rw-r--r--src/swap.js16
1 files changed, 16 insertions, 0 deletions
diff --git a/src/swap.js b/src/swap.js
index 3d4cf54..de89214 100644
--- a/src/swap.js
+++ b/src/swap.js
@@ -250,6 +250,22 @@ export class SwapManager {
_stop(id) { const t = this.timers.get(id); if (t) clearInterval(t); this.timers.delete(id); }
_spendFee() { return Math.max(250, Math.ceil(170 * this.feeRate)); } // ~1-input taproot spend
+ // The selected provider's reverse-swap limits (sat), fetched + cached per API.
+ // Lets the UI bound the amount to what the provider actually accepts instead of
+ // a hardcoded guess (providers + networks differ). Falls back conservatively.
+ async reverseLimits() {
+ const api = this.getApi();
+ if (this._revLim && this._revLimApi === api) return this._revLim;
+ let lim = { min: 25000, max: 25000000 };
+ try {
+ const res = await boltzReq(api, '/v2/swap/reverse');
+ const b = res && res.BTC && res.BTC.BTC && res.BTC.BTC.limits;
+ if (b && b.minimal) lim = { min: b.minimal, max: b.maximal };
+ } catch {}
+ this._revLim = lim; this._revLimApi = api;
+ return lim;
+ }
+
// REVERSE: hal receives over Lightning. Returns a record whose `.invoice`
// (bolt11) the user has someone pay; hal then claims the lockup on-chain.
async startReverse(amountSat) {