thunder-bridge 1.4.2 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +135 -125
- package/dist/bank-B3mHISn1.d.cts +92 -0
- package/dist/bank-B3mHISn1.d.ts +92 -0
- package/dist/bank.cjs +141 -0
- package/dist/bank.d.cts +44 -0
- package/dist/bank.d.ts +44 -0
- package/dist/bank.js +114 -0
- package/dist/client-Cc5gtjGV.d.ts +733 -0
- package/dist/client-CzGZcByI.d.cts +733 -0
- package/dist/errors-0vbVoISA.d.ts +126 -0
- package/dist/errors-Dmh-Uoh8.d.cts +126 -0
- package/dist/index.cjs +1576 -1094
- package/dist/index.d.cts +11 -503
- package/dist/index.d.ts +11 -503
- package/dist/index.js +1556 -1052
- package/dist/{server.cjs → nwc.cjs} +261 -689
- package/dist/nwc.d.cts +120 -0
- package/dist/nwc.d.ts +120 -0
- package/dist/{server.js → nwc.js} +256 -667
- package/dist/price.cjs +240 -0
- package/dist/price.d.cts +17 -0
- package/dist/price.d.ts +17 -0
- package/dist/price.js +205 -0
- package/dist/qr-CF-YeXU1.d.cts +55 -0
- package/dist/qr-CF-YeXU1.d.ts +55 -0
- package/dist/qr.cjs +262 -0
- package/dist/qr.d.cts +1 -0
- package/dist/qr.d.ts +1 -0
- package/dist/qr.js +227 -0
- package/dist/types-BNPmVnA7.d.cts +252 -0
- package/dist/types-BNPmVnA7.d.ts +252 -0
- package/openapi.yaml +1 -1
- package/package.json +48 -9
- package/dist/rail-CqUfuYXJ.d.cts +0 -615
- package/dist/rail-CqUfuYXJ.d.ts +0 -615
- package/dist/server.d.cts +0 -145
- package/dist/server.d.ts +0 -145
|
@@ -0,0 +1,252 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* How many minor units of `currency` one bitcoin costs at one venue, so 134883815
|
|
3
|
+
* is 1,348,838.15 CZK. Throws when that venue does not quote that currency, which
|
|
4
|
+
* is a normal answer rather than a fault: Kraken and Bitstamp have no CZK pair
|
|
5
|
+
*
|
|
6
|
+
* This is the plugin seam for prices. Another venue is another function of this
|
|
7
|
+
* shape
|
|
8
|
+
*/
|
|
9
|
+
type Ticker = (currency: string) => Promise<number>;
|
|
10
|
+
/** How many venues have to agree, how far apart they may be, and how long an answer is held */
|
|
11
|
+
interface MedianOptions {
|
|
12
|
+
/**
|
|
13
|
+
* How many venues have to answer before a price is usable. Two is the floor
|
|
14
|
+
* worth having, because one venue is a number nobody checked
|
|
15
|
+
*/
|
|
16
|
+
minVenues?: number;
|
|
17
|
+
/**
|
|
18
|
+
* Refuse the lot when the cheapest and dearest answers are further apart than
|
|
19
|
+
* this many basis points. Venues normally sit inside 50, so a wider spread means
|
|
20
|
+
* one of them is broken or stale rather than that the market moved
|
|
21
|
+
*/
|
|
22
|
+
maxSpreadBps?: number;
|
|
23
|
+
/** Hold the last answer this long per currency, so an order page is not four requests */
|
|
24
|
+
holdForSecs?: number;
|
|
25
|
+
}
|
|
26
|
+
/** Coinbase, CASP authorised in Luxembourg. Quotes CZK, EUR and most fiat */
|
|
27
|
+
declare function coinbase(baseUrl?: string): Ticker;
|
|
28
|
+
/** Kraken, CASP authorised by the Central Bank of Ireland. Quotes EUR and USD, no CZK */
|
|
29
|
+
declare function kraken(baseUrl?: string): Ticker;
|
|
30
|
+
/**
|
|
31
|
+
* Bitstamp, CASP authorised by the CSSF in Luxembourg. Quotes EUR and USD, no CZK.
|
|
32
|
+
*
|
|
33
|
+
* An unknown pair is answered with a `200` and the whole ticker list, whose first
|
|
34
|
+
* entry is BTC/USD, so asking it for CZK and reading the number would quote a
|
|
35
|
+
* bitcoin at 64,000 crowns. Anything but a single object is therefore refused
|
|
36
|
+
*/
|
|
37
|
+
declare function bitstamp(baseUrl?: string): Ticker;
|
|
38
|
+
/** Coinmate, on the ESMA CASP register, Czech and the one with a real BTC/CZK book */
|
|
39
|
+
declare function coinmate(baseUrl?: string): Ticker;
|
|
40
|
+
/**
|
|
41
|
+
* Ask several venues and take the middle answer, refusing the lot when they
|
|
42
|
+
* disagree too much.
|
|
43
|
+
*
|
|
44
|
+
* The default is the four MiCA authorised venues below, and every one of them is
|
|
45
|
+
* replaceable: pass your own list, or one venue, or a function that reads a price
|
|
46
|
+
* you already have. A venue that does not quote the currency is skipped rather
|
|
47
|
+
* than fatal, which for CZK leaves Coinbase and Coinmate.
|
|
48
|
+
*
|
|
49
|
+
* The middle is taken rather than the mean so one stuck venue moves the answer by
|
|
50
|
+
* nothing instead of by half its error, and the spread check is what catches the
|
|
51
|
+
* stuck venue that stays inside the pack.
|
|
52
|
+
*/
|
|
53
|
+
declare function medianOf(tickers?: Ticker[], options?: MedianOptions): Ticker;
|
|
54
|
+
/**
|
|
55
|
+
* What to ask for over Lightning for a price named in fiat, in millisatoshi.
|
|
56
|
+
*
|
|
57
|
+
* `priceMinorPerBtc` is what a `Ticker` returns. The arithmetic is exact, in
|
|
58
|
+
* BigInt, because a million crown order times a hundred billion millisatoshi
|
|
59
|
+
* leaves what a double can count, and it rounds up, because the extra
|
|
60
|
+
* millisatoshi is worth nothing and belongs to the recipient rather than to a
|
|
61
|
+
* rounding rule.
|
|
62
|
+
*
|
|
63
|
+
* `spreadBps` is yours to set, in basis points, and defaults to none. A Lightning
|
|
64
|
+
* invoice lives an hour and a bank transfer takes days, so a shop pricing in fiat is
|
|
65
|
+
* carrying that volatility whether or not it charges for it
|
|
66
|
+
*/
|
|
67
|
+
declare function msatFor(amountMinor: number, priceMinorPerBtc: number, options?: {
|
|
68
|
+
spreadBps?: number;
|
|
69
|
+
}): number;
|
|
70
|
+
|
|
71
|
+
declare const brand: unique symbol;
|
|
72
|
+
/**
|
|
73
|
+
* A whole number of millisatoshi that came from `sats`, `msat` or `fiat`, and
|
|
74
|
+
* could not have come from anywhere else.
|
|
75
|
+
*
|
|
76
|
+
* The brand is why: a bare number is not one of these, so `21` cannot be passed
|
|
77
|
+
* where a price is wanted and quietly mean twenty-one thousandths of a satoshi.
|
|
78
|
+
* It costs nothing at runtime, where the value is an ordinary number
|
|
79
|
+
*/
|
|
80
|
+
type Msat = number & {
|
|
81
|
+
readonly [brand]: "Msat";
|
|
82
|
+
};
|
|
83
|
+
/**
|
|
84
|
+
* What a payment is worth. A `Msat` is a price known now, and a function is one
|
|
85
|
+
* worked out when the invoice is minted, which is what a fiat price has to be.
|
|
86
|
+
*
|
|
87
|
+
* Build one with `sats`, `msat` or `fiat`
|
|
88
|
+
*/
|
|
89
|
+
type Amount = Msat | (() => Msat | Promise<Msat>);
|
|
90
|
+
/** How a fiat price is turned into millisatoshi at the moment of minting */
|
|
91
|
+
interface FiatOptions {
|
|
92
|
+
/**
|
|
93
|
+
* Where the rate comes from, the median of the four MiCA authorised venues by
|
|
94
|
+
* default. Pass your own to price off one venue, off your own book, or off a
|
|
95
|
+
* number you already hold
|
|
96
|
+
*/
|
|
97
|
+
rate?: Ticker;
|
|
98
|
+
/**
|
|
99
|
+
* What you add over the rate, in basis points, none by default. A Lightning
|
|
100
|
+
* invoice lives an hour and a bank transfer takes days, so a shop pricing in
|
|
101
|
+
* fiat carries that volatility whether or not it charges for it
|
|
102
|
+
*/
|
|
103
|
+
spreadBps?: number;
|
|
104
|
+
}
|
|
105
|
+
/** A whole number of satoshi, so `sats(21)` is 21000 millisatoshi */
|
|
106
|
+
declare function sats(whole: number): Msat;
|
|
107
|
+
/** An exact number of millisatoshi, for a price already in the smallest unit */
|
|
108
|
+
declare function msat(exact: number): Msat;
|
|
109
|
+
/**
|
|
110
|
+
* A price named in fiat, converted when the invoice is minted rather than now.
|
|
111
|
+
*
|
|
112
|
+
* Name it as a string and it is read digit by digit, exactly. Name it as a
|
|
113
|
+
* number and it is rounded to the currency's ISO 4217 minor unit, because
|
|
114
|
+
* binary floating point cannot hold 4.99 and a payment library that pretends
|
|
115
|
+
* otherwise moves the wrong amount.
|
|
116
|
+
*
|
|
117
|
+
* Every conversion asks the rate afresh, so two calls a second apart can
|
|
118
|
+
* differ. That is the honest behaviour for a fiat price, and the reason an
|
|
119
|
+
* amount is a function rather than a number.
|
|
120
|
+
*
|
|
121
|
+
* The answer is rounded up to a whole satoshi, because a wallet issues an
|
|
122
|
+
* invoice in satoshi and refuses a fraction of one. Up rather than down, so the
|
|
123
|
+
* rounding is never the shop's loss. `msatFor` is the raw conversion, for a rail
|
|
124
|
+
* that has no invoice to round for
|
|
125
|
+
*/
|
|
126
|
+
declare function fiat(major: number | string, currency: string, options?: FiatOptions): () => Promise<Msat>;
|
|
127
|
+
|
|
128
|
+
/** Where a payment stands, `paid` is the only status that carries a preimage */
|
|
129
|
+
type PaymentStatus = "pending" | "paid" | "expired";
|
|
130
|
+
interface Reported {
|
|
131
|
+
id: string;
|
|
132
|
+
status: PaymentStatus;
|
|
133
|
+
paymentHash: string;
|
|
134
|
+
verifyUrl: string;
|
|
135
|
+
preimage: string | null;
|
|
136
|
+
expiresAt: number;
|
|
137
|
+
createdAt: number;
|
|
138
|
+
/** What the watcher needs and the gateway cannot read, `unseal` opens it */
|
|
139
|
+
sealed: string | null;
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* A payment the gateway minted. It resolved the address itself, so it knows who
|
|
143
|
+
* is paid, how much, and which invoice says so, and none of the three can be
|
|
144
|
+
* null here
|
|
145
|
+
*/
|
|
146
|
+
interface MintedPayment extends Reported {
|
|
147
|
+
kind: "minted";
|
|
148
|
+
lnAddress: string;
|
|
149
|
+
amountMsat: number;
|
|
150
|
+
bolt11: string;
|
|
151
|
+
}
|
|
152
|
+
/**
|
|
153
|
+
* A payment the gateway was handed rather than asked to mint. It was told a hash,
|
|
154
|
+
* a URL and an expiry and nothing else, which is the point of `watch`, so the
|
|
155
|
+
* address, the amount and the invoice are all absent rather than merely unknown
|
|
156
|
+
*/
|
|
157
|
+
interface WatchedPayment extends Reported {
|
|
158
|
+
kind: "watched";
|
|
159
|
+
lnAddress: null;
|
|
160
|
+
amountMsat: null;
|
|
161
|
+
bolt11: null;
|
|
162
|
+
}
|
|
163
|
+
/**
|
|
164
|
+
* A payment as the gateway reports it, of either sort. Check `kind` and the
|
|
165
|
+
* three fields a watched payment does not carry stop being null, so nothing here
|
|
166
|
+
* needs an assertion to read
|
|
167
|
+
*/
|
|
168
|
+
type Payment = MintedPayment | WatchedPayment;
|
|
169
|
+
/**
|
|
170
|
+
* Who is paid and how much. `to` is a priority list when it is an array: the
|
|
171
|
+
* gateway takes the first address that can issue a provable invoice for the
|
|
172
|
+
* amount and the rest are the fallback
|
|
173
|
+
*/
|
|
174
|
+
interface Charge {
|
|
175
|
+
paidTo: string | string[];
|
|
176
|
+
amount: Amount;
|
|
177
|
+
/** Where the gateway posts the settlement, signed with the key it publishes */
|
|
178
|
+
webhookUrl?: string;
|
|
179
|
+
}
|
|
180
|
+
/**
|
|
181
|
+
* A charge with its price settled, which is what a proof compares the gateway's
|
|
182
|
+
* answer against. Asking a fiat price twice gives two numbers, so the proof is
|
|
183
|
+
* handed the one that was actually asked for
|
|
184
|
+
*/
|
|
185
|
+
interface Priced {
|
|
186
|
+
paidTo: string[];
|
|
187
|
+
amountMsat: number;
|
|
188
|
+
}
|
|
189
|
+
/**
|
|
190
|
+
* An invoice you obtained yourself, handed over to be watched. The gateway is
|
|
191
|
+
* given no address and no amount, so it cannot refuse one recipient rather than
|
|
192
|
+
* all of them
|
|
193
|
+
*/
|
|
194
|
+
interface Handover {
|
|
195
|
+
paymentHash: string;
|
|
196
|
+
verifyUrl: string;
|
|
197
|
+
expiresAt: number;
|
|
198
|
+
/** Groups this payment with every other one carrying the same secret */
|
|
199
|
+
trigger?: string;
|
|
200
|
+
/**
|
|
201
|
+
* How many of this trigger's settlements the gateway keeps replayable past the
|
|
202
|
+
* hour it would otherwise forget them in, up to the ceiling its operator set.
|
|
203
|
+
* Needs `trigger`, defaults to none
|
|
204
|
+
*/
|
|
205
|
+
replay?: number;
|
|
206
|
+
/** Sealed with `seal`, so the gateway stores what it cannot read */
|
|
207
|
+
sealed?: string;
|
|
208
|
+
webhookUrl?: string;
|
|
209
|
+
}
|
|
210
|
+
/**
|
|
211
|
+
* Which address would serve an amount, and what the ones ahead of it refused.
|
|
212
|
+
* `feeMsat` is always zero, the payer pays the recipient's own invoice and the
|
|
213
|
+
* gateway is never in the money's path
|
|
214
|
+
*/
|
|
215
|
+
interface Quote {
|
|
216
|
+
lnAddress: string;
|
|
217
|
+
amountMsat: number;
|
|
218
|
+
feeMsat: number;
|
|
219
|
+
minMsat: number;
|
|
220
|
+
maxMsat: number;
|
|
221
|
+
metadata: string;
|
|
222
|
+
refusals: WalletFailure[];
|
|
223
|
+
}
|
|
224
|
+
/**
|
|
225
|
+
* A one minute pass onto one trigger's stream. It opens that trigger and nothing
|
|
226
|
+
* else, which is what makes it the thing to hand a browser when the trigger
|
|
227
|
+
* secret is not. `expiresAt` is unix seconds, like every other time here
|
|
228
|
+
*/
|
|
229
|
+
interface SocketTicket {
|
|
230
|
+
ticket: string;
|
|
231
|
+
expiresAt: number;
|
|
232
|
+
}
|
|
233
|
+
/** Why one wallet in the list could not be used */
|
|
234
|
+
type WalletReason = "address-unusable" | "unreachable" | "amount-not-accepted" | "cannot-prove-delivery" | "invoice-refused";
|
|
235
|
+
/** One wallet on the list that could not be used, and the reason it could not */
|
|
236
|
+
interface WalletFailure {
|
|
237
|
+
address: string;
|
|
238
|
+
reason: WalletReason;
|
|
239
|
+
}
|
|
240
|
+
/**
|
|
241
|
+
* What a delivery carries. Everything needed to act on a settlement and to check
|
|
242
|
+
* it, and nothing else, so a retry is the same size every time
|
|
243
|
+
*/
|
|
244
|
+
interface Settlement {
|
|
245
|
+
id: string;
|
|
246
|
+
status: PaymentStatus;
|
|
247
|
+
paymentHash: string;
|
|
248
|
+
preimage: string | null;
|
|
249
|
+
settledAt: number;
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
export { type Amount as A, type Charge as C, type FiatOptions as F, type Handover as H, type MedianOptions as M, type Payment as P, type Quote as Q, type Settlement as S, type Ticker as T, type WalletFailure as W, coinmate as a, bitstamp as b, coinbase as c, msatFor as d, type MintedPayment as e, type Msat as f, type PaymentStatus as g, type Priced as h, type SocketTicket as i, type WalletReason as j, kraken as k, type WatchedPayment as l, medianOf as m, fiat as n, msat as o, sats as s };
|
|
@@ -0,0 +1,252 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* How many minor units of `currency` one bitcoin costs at one venue, so 134883815
|
|
3
|
+
* is 1,348,838.15 CZK. Throws when that venue does not quote that currency, which
|
|
4
|
+
* is a normal answer rather than a fault: Kraken and Bitstamp have no CZK pair
|
|
5
|
+
*
|
|
6
|
+
* This is the plugin seam for prices. Another venue is another function of this
|
|
7
|
+
* shape
|
|
8
|
+
*/
|
|
9
|
+
type Ticker = (currency: string) => Promise<number>;
|
|
10
|
+
/** How many venues have to agree, how far apart they may be, and how long an answer is held */
|
|
11
|
+
interface MedianOptions {
|
|
12
|
+
/**
|
|
13
|
+
* How many venues have to answer before a price is usable. Two is the floor
|
|
14
|
+
* worth having, because one venue is a number nobody checked
|
|
15
|
+
*/
|
|
16
|
+
minVenues?: number;
|
|
17
|
+
/**
|
|
18
|
+
* Refuse the lot when the cheapest and dearest answers are further apart than
|
|
19
|
+
* this many basis points. Venues normally sit inside 50, so a wider spread means
|
|
20
|
+
* one of them is broken or stale rather than that the market moved
|
|
21
|
+
*/
|
|
22
|
+
maxSpreadBps?: number;
|
|
23
|
+
/** Hold the last answer this long per currency, so an order page is not four requests */
|
|
24
|
+
holdForSecs?: number;
|
|
25
|
+
}
|
|
26
|
+
/** Coinbase, CASP authorised in Luxembourg. Quotes CZK, EUR and most fiat */
|
|
27
|
+
declare function coinbase(baseUrl?: string): Ticker;
|
|
28
|
+
/** Kraken, CASP authorised by the Central Bank of Ireland. Quotes EUR and USD, no CZK */
|
|
29
|
+
declare function kraken(baseUrl?: string): Ticker;
|
|
30
|
+
/**
|
|
31
|
+
* Bitstamp, CASP authorised by the CSSF in Luxembourg. Quotes EUR and USD, no CZK.
|
|
32
|
+
*
|
|
33
|
+
* An unknown pair is answered with a `200` and the whole ticker list, whose first
|
|
34
|
+
* entry is BTC/USD, so asking it for CZK and reading the number would quote a
|
|
35
|
+
* bitcoin at 64,000 crowns. Anything but a single object is therefore refused
|
|
36
|
+
*/
|
|
37
|
+
declare function bitstamp(baseUrl?: string): Ticker;
|
|
38
|
+
/** Coinmate, on the ESMA CASP register, Czech and the one with a real BTC/CZK book */
|
|
39
|
+
declare function coinmate(baseUrl?: string): Ticker;
|
|
40
|
+
/**
|
|
41
|
+
* Ask several venues and take the middle answer, refusing the lot when they
|
|
42
|
+
* disagree too much.
|
|
43
|
+
*
|
|
44
|
+
* The default is the four MiCA authorised venues below, and every one of them is
|
|
45
|
+
* replaceable: pass your own list, or one venue, or a function that reads a price
|
|
46
|
+
* you already have. A venue that does not quote the currency is skipped rather
|
|
47
|
+
* than fatal, which for CZK leaves Coinbase and Coinmate.
|
|
48
|
+
*
|
|
49
|
+
* The middle is taken rather than the mean so one stuck venue moves the answer by
|
|
50
|
+
* nothing instead of by half its error, and the spread check is what catches the
|
|
51
|
+
* stuck venue that stays inside the pack.
|
|
52
|
+
*/
|
|
53
|
+
declare function medianOf(tickers?: Ticker[], options?: MedianOptions): Ticker;
|
|
54
|
+
/**
|
|
55
|
+
* What to ask for over Lightning for a price named in fiat, in millisatoshi.
|
|
56
|
+
*
|
|
57
|
+
* `priceMinorPerBtc` is what a `Ticker` returns. The arithmetic is exact, in
|
|
58
|
+
* BigInt, because a million crown order times a hundred billion millisatoshi
|
|
59
|
+
* leaves what a double can count, and it rounds up, because the extra
|
|
60
|
+
* millisatoshi is worth nothing and belongs to the recipient rather than to a
|
|
61
|
+
* rounding rule.
|
|
62
|
+
*
|
|
63
|
+
* `spreadBps` is yours to set, in basis points, and defaults to none. A Lightning
|
|
64
|
+
* invoice lives an hour and a bank transfer takes days, so a shop pricing in fiat is
|
|
65
|
+
* carrying that volatility whether or not it charges for it
|
|
66
|
+
*/
|
|
67
|
+
declare function msatFor(amountMinor: number, priceMinorPerBtc: number, options?: {
|
|
68
|
+
spreadBps?: number;
|
|
69
|
+
}): number;
|
|
70
|
+
|
|
71
|
+
declare const brand: unique symbol;
|
|
72
|
+
/**
|
|
73
|
+
* A whole number of millisatoshi that came from `sats`, `msat` or `fiat`, and
|
|
74
|
+
* could not have come from anywhere else.
|
|
75
|
+
*
|
|
76
|
+
* The brand is why: a bare number is not one of these, so `21` cannot be passed
|
|
77
|
+
* where a price is wanted and quietly mean twenty-one thousandths of a satoshi.
|
|
78
|
+
* It costs nothing at runtime, where the value is an ordinary number
|
|
79
|
+
*/
|
|
80
|
+
type Msat = number & {
|
|
81
|
+
readonly [brand]: "Msat";
|
|
82
|
+
};
|
|
83
|
+
/**
|
|
84
|
+
* What a payment is worth. A `Msat` is a price known now, and a function is one
|
|
85
|
+
* worked out when the invoice is minted, which is what a fiat price has to be.
|
|
86
|
+
*
|
|
87
|
+
* Build one with `sats`, `msat` or `fiat`
|
|
88
|
+
*/
|
|
89
|
+
type Amount = Msat | (() => Msat | Promise<Msat>);
|
|
90
|
+
/** How a fiat price is turned into millisatoshi at the moment of minting */
|
|
91
|
+
interface FiatOptions {
|
|
92
|
+
/**
|
|
93
|
+
* Where the rate comes from, the median of the four MiCA authorised venues by
|
|
94
|
+
* default. Pass your own to price off one venue, off your own book, or off a
|
|
95
|
+
* number you already hold
|
|
96
|
+
*/
|
|
97
|
+
rate?: Ticker;
|
|
98
|
+
/**
|
|
99
|
+
* What you add over the rate, in basis points, none by default. A Lightning
|
|
100
|
+
* invoice lives an hour and a bank transfer takes days, so a shop pricing in
|
|
101
|
+
* fiat carries that volatility whether or not it charges for it
|
|
102
|
+
*/
|
|
103
|
+
spreadBps?: number;
|
|
104
|
+
}
|
|
105
|
+
/** A whole number of satoshi, so `sats(21)` is 21000 millisatoshi */
|
|
106
|
+
declare function sats(whole: number): Msat;
|
|
107
|
+
/** An exact number of millisatoshi, for a price already in the smallest unit */
|
|
108
|
+
declare function msat(exact: number): Msat;
|
|
109
|
+
/**
|
|
110
|
+
* A price named in fiat, converted when the invoice is minted rather than now.
|
|
111
|
+
*
|
|
112
|
+
* Name it as a string and it is read digit by digit, exactly. Name it as a
|
|
113
|
+
* number and it is rounded to the currency's ISO 4217 minor unit, because
|
|
114
|
+
* binary floating point cannot hold 4.99 and a payment library that pretends
|
|
115
|
+
* otherwise moves the wrong amount.
|
|
116
|
+
*
|
|
117
|
+
* Every conversion asks the rate afresh, so two calls a second apart can
|
|
118
|
+
* differ. That is the honest behaviour for a fiat price, and the reason an
|
|
119
|
+
* amount is a function rather than a number.
|
|
120
|
+
*
|
|
121
|
+
* The answer is rounded up to a whole satoshi, because a wallet issues an
|
|
122
|
+
* invoice in satoshi and refuses a fraction of one. Up rather than down, so the
|
|
123
|
+
* rounding is never the shop's loss. `msatFor` is the raw conversion, for a rail
|
|
124
|
+
* that has no invoice to round for
|
|
125
|
+
*/
|
|
126
|
+
declare function fiat(major: number | string, currency: string, options?: FiatOptions): () => Promise<Msat>;
|
|
127
|
+
|
|
128
|
+
/** Where a payment stands, `paid` is the only status that carries a preimage */
|
|
129
|
+
type PaymentStatus = "pending" | "paid" | "expired";
|
|
130
|
+
interface Reported {
|
|
131
|
+
id: string;
|
|
132
|
+
status: PaymentStatus;
|
|
133
|
+
paymentHash: string;
|
|
134
|
+
verifyUrl: string;
|
|
135
|
+
preimage: string | null;
|
|
136
|
+
expiresAt: number;
|
|
137
|
+
createdAt: number;
|
|
138
|
+
/** What the watcher needs and the gateway cannot read, `unseal` opens it */
|
|
139
|
+
sealed: string | null;
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* A payment the gateway minted. It resolved the address itself, so it knows who
|
|
143
|
+
* is paid, how much, and which invoice says so, and none of the three can be
|
|
144
|
+
* null here
|
|
145
|
+
*/
|
|
146
|
+
interface MintedPayment extends Reported {
|
|
147
|
+
kind: "minted";
|
|
148
|
+
lnAddress: string;
|
|
149
|
+
amountMsat: number;
|
|
150
|
+
bolt11: string;
|
|
151
|
+
}
|
|
152
|
+
/**
|
|
153
|
+
* A payment the gateway was handed rather than asked to mint. It was told a hash,
|
|
154
|
+
* a URL and an expiry and nothing else, which is the point of `watch`, so the
|
|
155
|
+
* address, the amount and the invoice are all absent rather than merely unknown
|
|
156
|
+
*/
|
|
157
|
+
interface WatchedPayment extends Reported {
|
|
158
|
+
kind: "watched";
|
|
159
|
+
lnAddress: null;
|
|
160
|
+
amountMsat: null;
|
|
161
|
+
bolt11: null;
|
|
162
|
+
}
|
|
163
|
+
/**
|
|
164
|
+
* A payment as the gateway reports it, of either sort. Check `kind` and the
|
|
165
|
+
* three fields a watched payment does not carry stop being null, so nothing here
|
|
166
|
+
* needs an assertion to read
|
|
167
|
+
*/
|
|
168
|
+
type Payment = MintedPayment | WatchedPayment;
|
|
169
|
+
/**
|
|
170
|
+
* Who is paid and how much. `to` is a priority list when it is an array: the
|
|
171
|
+
* gateway takes the first address that can issue a provable invoice for the
|
|
172
|
+
* amount and the rest are the fallback
|
|
173
|
+
*/
|
|
174
|
+
interface Charge {
|
|
175
|
+
paidTo: string | string[];
|
|
176
|
+
amount: Amount;
|
|
177
|
+
/** Where the gateway posts the settlement, signed with the key it publishes */
|
|
178
|
+
webhookUrl?: string;
|
|
179
|
+
}
|
|
180
|
+
/**
|
|
181
|
+
* A charge with its price settled, which is what a proof compares the gateway's
|
|
182
|
+
* answer against. Asking a fiat price twice gives two numbers, so the proof is
|
|
183
|
+
* handed the one that was actually asked for
|
|
184
|
+
*/
|
|
185
|
+
interface Priced {
|
|
186
|
+
paidTo: string[];
|
|
187
|
+
amountMsat: number;
|
|
188
|
+
}
|
|
189
|
+
/**
|
|
190
|
+
* An invoice you obtained yourself, handed over to be watched. The gateway is
|
|
191
|
+
* given no address and no amount, so it cannot refuse one recipient rather than
|
|
192
|
+
* all of them
|
|
193
|
+
*/
|
|
194
|
+
interface Handover {
|
|
195
|
+
paymentHash: string;
|
|
196
|
+
verifyUrl: string;
|
|
197
|
+
expiresAt: number;
|
|
198
|
+
/** Groups this payment with every other one carrying the same secret */
|
|
199
|
+
trigger?: string;
|
|
200
|
+
/**
|
|
201
|
+
* How many of this trigger's settlements the gateway keeps replayable past the
|
|
202
|
+
* hour it would otherwise forget them in, up to the ceiling its operator set.
|
|
203
|
+
* Needs `trigger`, defaults to none
|
|
204
|
+
*/
|
|
205
|
+
replay?: number;
|
|
206
|
+
/** Sealed with `seal`, so the gateway stores what it cannot read */
|
|
207
|
+
sealed?: string;
|
|
208
|
+
webhookUrl?: string;
|
|
209
|
+
}
|
|
210
|
+
/**
|
|
211
|
+
* Which address would serve an amount, and what the ones ahead of it refused.
|
|
212
|
+
* `feeMsat` is always zero, the payer pays the recipient's own invoice and the
|
|
213
|
+
* gateway is never in the money's path
|
|
214
|
+
*/
|
|
215
|
+
interface Quote {
|
|
216
|
+
lnAddress: string;
|
|
217
|
+
amountMsat: number;
|
|
218
|
+
feeMsat: number;
|
|
219
|
+
minMsat: number;
|
|
220
|
+
maxMsat: number;
|
|
221
|
+
metadata: string;
|
|
222
|
+
refusals: WalletFailure[];
|
|
223
|
+
}
|
|
224
|
+
/**
|
|
225
|
+
* A one minute pass onto one trigger's stream. It opens that trigger and nothing
|
|
226
|
+
* else, which is what makes it the thing to hand a browser when the trigger
|
|
227
|
+
* secret is not. `expiresAt` is unix seconds, like every other time here
|
|
228
|
+
*/
|
|
229
|
+
interface SocketTicket {
|
|
230
|
+
ticket: string;
|
|
231
|
+
expiresAt: number;
|
|
232
|
+
}
|
|
233
|
+
/** Why one wallet in the list could not be used */
|
|
234
|
+
type WalletReason = "address-unusable" | "unreachable" | "amount-not-accepted" | "cannot-prove-delivery" | "invoice-refused";
|
|
235
|
+
/** One wallet on the list that could not be used, and the reason it could not */
|
|
236
|
+
interface WalletFailure {
|
|
237
|
+
address: string;
|
|
238
|
+
reason: WalletReason;
|
|
239
|
+
}
|
|
240
|
+
/**
|
|
241
|
+
* What a delivery carries. Everything needed to act on a settlement and to check
|
|
242
|
+
* it, and nothing else, so a retry is the same size every time
|
|
243
|
+
*/
|
|
244
|
+
interface Settlement {
|
|
245
|
+
id: string;
|
|
246
|
+
status: PaymentStatus;
|
|
247
|
+
paymentHash: string;
|
|
248
|
+
preimage: string | null;
|
|
249
|
+
settledAt: number;
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
export { type Amount as A, type Charge as C, type FiatOptions as F, type Handover as H, type MedianOptions as M, type Payment as P, type Quote as Q, type Settlement as S, type Ticker as T, type WalletFailure as W, coinmate as a, bitstamp as b, coinbase as c, msatFor as d, type MintedPayment as e, type Msat as f, type PaymentStatus as g, type Priced as h, type SocketTicket as i, type WalletReason as j, kraken as k, type WatchedPayment as l, medianOf as m, fiat as n, msat as o, sats as s };
|
package/openapi.yaml
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "thunder-bridge",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.5.0",
|
|
4
4
|
"description": "Trustless JavaScript client for the Thunder Bridge Lightning payment gateway. Proves the invoice came from your own wallet before the payer sees it.",
|
|
5
5
|
"author": "i-am-fatik",
|
|
6
6
|
"homepage": "https://agora.gripe/en/tools/thunder-bridge",
|
|
@@ -17,8 +17,17 @@
|
|
|
17
17
|
"types": "./dist/index.d.ts",
|
|
18
18
|
"typesVersions": {
|
|
19
19
|
"*": {
|
|
20
|
-
"
|
|
21
|
-
"./dist/
|
|
20
|
+
"qr": [
|
|
21
|
+
"./dist/qr.d.ts"
|
|
22
|
+
],
|
|
23
|
+
"price": [
|
|
24
|
+
"./dist/price.d.ts"
|
|
25
|
+
],
|
|
26
|
+
"bank": [
|
|
27
|
+
"./dist/bank.d.ts"
|
|
28
|
+
],
|
|
29
|
+
"nwc": [
|
|
30
|
+
"./dist/nwc.d.ts"
|
|
22
31
|
]
|
|
23
32
|
}
|
|
24
33
|
},
|
|
@@ -33,14 +42,44 @@
|
|
|
33
42
|
"default": "./dist/index.cjs"
|
|
34
43
|
}
|
|
35
44
|
},
|
|
36
|
-
"./
|
|
45
|
+
"./qr": {
|
|
37
46
|
"import": {
|
|
38
|
-
"types": "./dist/
|
|
39
|
-
"default": "./dist/
|
|
47
|
+
"types": "./dist/qr.d.ts",
|
|
48
|
+
"default": "./dist/qr.js"
|
|
40
49
|
},
|
|
41
50
|
"require": {
|
|
42
|
-
"types": "./dist/
|
|
43
|
-
"default": "./dist/
|
|
51
|
+
"types": "./dist/qr.d.cts",
|
|
52
|
+
"default": "./dist/qr.cjs"
|
|
53
|
+
}
|
|
54
|
+
},
|
|
55
|
+
"./price": {
|
|
56
|
+
"import": {
|
|
57
|
+
"types": "./dist/price.d.ts",
|
|
58
|
+
"default": "./dist/price.js"
|
|
59
|
+
},
|
|
60
|
+
"require": {
|
|
61
|
+
"types": "./dist/price.d.cts",
|
|
62
|
+
"default": "./dist/price.cjs"
|
|
63
|
+
}
|
|
64
|
+
},
|
|
65
|
+
"./bank": {
|
|
66
|
+
"import": {
|
|
67
|
+
"types": "./dist/bank.d.ts",
|
|
68
|
+
"default": "./dist/bank.js"
|
|
69
|
+
},
|
|
70
|
+
"require": {
|
|
71
|
+
"types": "./dist/bank.d.cts",
|
|
72
|
+
"default": "./dist/bank.cjs"
|
|
73
|
+
}
|
|
74
|
+
},
|
|
75
|
+
"./nwc": {
|
|
76
|
+
"import": {
|
|
77
|
+
"types": "./dist/nwc.d.ts",
|
|
78
|
+
"default": "./dist/nwc.js"
|
|
79
|
+
},
|
|
80
|
+
"require": {
|
|
81
|
+
"types": "./dist/nwc.d.cts",
|
|
82
|
+
"default": "./dist/nwc.cjs"
|
|
44
83
|
}
|
|
45
84
|
}
|
|
46
85
|
},
|
|
@@ -52,7 +91,7 @@
|
|
|
52
91
|
"node": ">=22"
|
|
53
92
|
},
|
|
54
93
|
"scripts": {
|
|
55
|
-
"build": "tsup
|
|
94
|
+
"build": "tsup",
|
|
56
95
|
"test": "vitest run",
|
|
57
96
|
"test:watch": "vitest",
|
|
58
97
|
"typecheck": "tsc --noEmit && tsc -p tsconfig.test.json",
|