@dcasegr/amm-client 0.39.0 → 0.42.2
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 +70 -31
- package/dist/client.d.ts +190 -62
- package/dist/client.js +493 -322
- package/dist/errors.d.ts +1 -1
- package/dist/errors.js +6 -3
- package/dist/index.d.ts +16 -4
- package/dist/index.js +16 -4
- package/dist/lib/overlay.d.ts +132 -50
- package/dist/lib/overlay.js +169 -160
- package/dist/lib/skein.d.ts +22 -0
- package/dist/lib/skein.js +16 -1
- package/dist/market/activeSwap.d.ts +77 -96
- package/dist/market/activeSwap.js +146 -166
- package/dist/market/plan.d.ts +2 -1
- package/dist/market/plan.js +1 -1
- package/dist/market/swapAction.d.ts +150 -145
- package/dist/market/swapAction.js +292 -213
- package/dist/market/swapFlow.d.ts +3 -6
- package/dist/market/swapFlow.js +4 -22
- package/dist/pool/pool.artifact.json +760 -528
- package/dist/pool/template.d.ts +10 -2
- package/dist/pool/template.js +16 -6
- package/dist/wallet/color.d.ts +13 -9
- package/dist/wallet/color.js +13 -10
- package/dist/wallet/swapPayouts.d.ts +45 -28
- package/dist/wallet/swapPayouts.js +129 -117
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -40,28 +40,47 @@ exchange with another wallet, keeping what was read and quoted.
|
|
|
40
40
|
The client (each an async function unless noted):
|
|
41
41
|
|
|
42
42
|
- the exchange: `enabledList`, `registeredTokens`, `tokenBaseOf`, `hostedTokens` (the token list
|
|
43
|
-
and ONE `GET /amm/stats`), `
|
|
44
|
-
|
|
45
|
-
|
|
43
|
+
and ONE `GET /amm/stats`), `tokenPools(tokenId)` (0.41.0: the token's pools route, a plain
|
|
44
|
+
read past the browser's cache), `watchPoolEvents(tokenId | "all", onEvent)` (0.41.0: the host's
|
|
45
|
+
pool event feed, `/@<token>/amm/events` or `<origin>/amm/events`; each message `{tokenId, …row}`,
|
|
46
|
+
a `/pools/history` row or a `revert`; signals for display, the pools route the truth; sync,
|
|
47
|
+
returns the unsubscribe; reconnect is the browser EventSource's),
|
|
46
48
|
`claimStatus`, `isRoot`, `claimExchange`, `discoveryBase` (sync), `onDataChange` (sync);
|
|
47
|
-
- history (0.
|
|
48
|
-
`
|
|
49
|
-
`
|
|
50
|
-
|
|
51
|
-
|
|
49
|
+
- history (plain GETs; 0.40.0: by pool id, `poolId` = the pool's deploy outpoint `<txid>_<vout>`):
|
|
50
|
+
`trades(tokenId, {from?, to?, limit?, before?, pool?})` → `{trades, next}` (each row its
|
|
51
|
+
`poolId` and `payoutPkh`), `trade(tokenId, txid)` → a `Trade` or null, `candles(tokenId, {tf,
|
|
52
|
+
from, to, series?})` (`series` `fill`, the default, or `market`), `stats(tokenId)` /
|
|
53
|
+
`statsAll({ids?, fresh?})` (`price` = the midpoint of what a buy and a sell of 1% of the pooled sats
|
|
54
|
+
would pay now, `buyPrice`, `sellPrice`, `lastTradePrice`), `holders(tokenId, {limit?, skip?})` →
|
|
55
|
+
`{count, rows}`, `positionsAll(poolIds)`, `poolsAt(tokenId, t)` (every pool listed at `t`),
|
|
56
|
+
`poolHistory(tokenId, {from?, to?, pool?, limit?, after?})` → `{events, next}` (oldest first;
|
|
57
|
+
forward paging: `next` as `after`), `spendsAll(outpoints)` (the host's `/amm/spends`); amounts
|
|
58
|
+
bigints, prices `{sats, tokens}` pairs of bigints (base units both);
|
|
52
59
|
- swap: `quoteSwap(request, poolsAnswer, {sym, dec})` (sync: the engine's plan over the pools the
|
|
53
|
-
token's pools
|
|
54
|
-
`
|
|
60
|
+
token's pools route gave, each pool with its validator's `minLegSats`; the quote's price and
|
|
61
|
+
impact from the engine's `priceOf`, each leg's own `fees`, `stage` = what Swap sets aside
|
|
62
|
+
(`amount`, `feeSats`: 0.40.2, exactly `maxSources` legs), `legMinerFeeSats`); the request's
|
|
63
|
+
`maxSources` (required, 0.40.2; replaces `allowPartial`) is the most pools the swap may draw on —
|
|
64
|
+
1 is exactly one leg; the Open Exchange pages send 1 or 5,
|
|
65
|
+
`executeSwap(quote, {onProgress, signal})` (below), `walletSats`;
|
|
55
66
|
- liquidity: `myPositions`, `validatorTerms`, `deployPosition({tokenId, tokens, sats})`,
|
|
56
67
|
`closePosition({outpoint})`, `rebalancePosition({outpoint, tokens, sats})` (the old pool closed
|
|
57
68
|
and a new one deployed in ONE wallet createAction);
|
|
58
|
-
- your tokens: `myTokens`, `settleSwaps` (the
|
|
59
|
-
|
|
69
|
+
- your tokens: `myTokens`, `settleSwaps` (the pass over the swap basket: a staged token output the
|
|
70
|
+
basket lacks filed from its action's description; then every row's spender, this wallet's legs
|
|
71
|
+
taken in: the txids), `swapBasketSats`, `moveBackTokens(tokenId)` (every row of the token and
|
|
72
|
+
every sats row: txid, amount, BEEF, submit), `moveBackStagedSats` (the sats alone), `sendTokens`;
|
|
60
73
|
- settings (root): `deployBeef`, `enableToken`, `tokensToEnable`, `disableToken`, `defaults`,
|
|
61
74
|
`setDefaultTerms`, `clearDefaultTerms`, `setDefaultMarket`, `clearDefaultMarket`, `tokenTerms`,
|
|
62
|
-
`setTokenTerms
|
|
63
|
-
|
|
64
|
-
|
|
75
|
+
`setTokenTerms` (0.40.0: the terms `{lpBps, validatorBps, commissionBps, minLegSats?}`), `discoveryState`, `setDiscovery`,
|
|
76
|
+
`setEnablePrice`, `exchangeWallet`, `withdrawAll`, `settleWithdrawals` (0.42.x);
|
|
77
|
+
- the paid enable (0.42.2, anyone signed; open-exchange 0.15.3): `enableTokenPaid(tokenId, {deployBeef?})` — the price
|
|
78
|
+
from `/amm/defaults`, a BRC-29 payment to the exchange built with `noSend` (not sent: the exchange's take-in sends it),
|
|
79
|
+
ONE BEEF with the deploy and the payment, `POST /amm/enable?tokenId=&paymentTxid=&paymentVout=&derivationPrefix=
|
|
80
|
+
&derivationSuffix=` signed; the enabled row back; on any refusal or failure the unsent payment is aborted
|
|
81
|
+
(`abortAction`). Refusals are `ClientError` kind `refused`, the exchange's code first in the message.
|
|
82
|
+
|
|
83
|
+
Pure helpers beside it: `hostedFrom`, `parsePoolEventMessage`, `poolViews`, `poolFees`, `poolsWithMinimums`, `pairPrice`, `legCarrySats`, `hasTerms`,
|
|
65
84
|
`enableCandidates`, `topicOf`, `lookupOf`, `ammLookupOf`, `walletDeployBeef`, `exchangeBase`,
|
|
66
85
|
`tokenBase`; the types (`Quote`, `SwapResult`, `LegResult`, `Position`, `WalletToken`, …).
|
|
67
86
|
|
|
@@ -69,15 +88,19 @@ Pure helpers beside it: `hostedFrom`, `applyPoolChange`, `parseChange`, `poolVie
|
|
|
69
88
|
|
|
70
89
|
An error of one of `CLIENT_ERROR_KINDS` is a `ClientError` with `kind` and the message the pages
|
|
71
90
|
show: `stale_pool`, `fee_mismatch`, `quote_mismatch`, `slippage`, `pool_spent`, `user_rejected`,
|
|
72
|
-
`no_answer`, `
|
|
73
|
-
`
|
|
91
|
+
`no_answer`, `below_minimum` (0.40.0: under a validator's minimum leg; a quote no pool takes),
|
|
92
|
+
`refused`, `network`. `errorKind(e)` classifies any error; other errors stay plain `Error`s.
|
|
74
93
|
|
|
75
94
|
## The shared names
|
|
76
95
|
|
|
77
96
|
What two sites must use to file identical wallet rows: `POOLS_BASKET` (`amm-pools`, the LP's
|
|
78
97
|
position rows), `SWAP_BASKET` (`amm-swap`, what swap legs spend), `SWAP_PROTOCOL` (`[2, "amm
|
|
79
|
-
swap"]`), `SWAP_KEY_PREFIX` + `
|
|
80
|
-
`
|
|
98
|
+
swap"]`), `SWAP_KEY_PREFIX` + `newSwapKeyID` (a staged row's random keyID), `changeKeyID` (a leg's
|
|
99
|
+
change row: `amm-swap-<txid>.<vout>:change` of its first input of that kind), `SWAP_STAGE_LABEL`
|
|
100
|
+
(`amm-swap-stage`) + `SWAP_KEY_MARK` + `swapKeyDescription` / `swapKeyIdOfDescription` (a staged
|
|
101
|
+
token output's description naming its key), `legDerivation` (an order's payout, own commission and
|
|
102
|
+
last-leg change keys), `swapInstructions` / `swapSatsInstructions` (their customInstructions, a
|
|
103
|
+
change row's with `order`), `LP_KEY_PROTOCOL` (BRC-29) + `LP_KEY_MARK` +
|
|
81
104
|
`lpKeyDescription` / `lpKeyIdOfDescription` (the deploy's pool output description naming the LP
|
|
82
105
|
keyID), `POOL_TAG` / `POOL_OP` / `isPoolRow` / `poolCustomInstructions` (an `amm-pools` row),
|
|
83
106
|
`POOL_DEPLOY_LABEL` (`amm-pool-deploy`), `SWAP_TTL_MS` (15 s), `transferPlanLabels` (the `p color
|
|
@@ -92,20 +115,36 @@ import { createClient, ClientError } from "@dcasegr/amm-client";
|
|
|
92
115
|
const client = createClient({ origin: "https://swap.skein.nexus", wallet });
|
|
93
116
|
const tokenId = "<txid>_0";
|
|
94
117
|
|
|
95
|
-
// The token's pools route
|
|
96
|
-
const
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
});
|
|
118
|
+
// The token's pools route: the pools a swap may use, the market (read again on a pool event).
|
|
119
|
+
const pools = await client.tokenPools(tokenId);
|
|
120
|
+
const quote = client.quoteSwap({ tokenId, side: "buy", amountIn: 50_000n, maxSlippageBps: 50, maxSources: 1 }, pools, { sym: "TOK", dec: 0 });
|
|
121
|
+
try {
|
|
122
|
+
const cancel = new AbortController();
|
|
123
|
+
const result = await client.executeSwap(quote, { signal: cancel.signal, onProgress: (p) => console.log(p.phase) });
|
|
124
|
+
console.log(result.status, result.stop, result.legs, result.returned);
|
|
125
|
+
} catch (e) {
|
|
126
|
+
if (e instanceof ClientError) console.log(e.kind, e.message);
|
|
127
|
+
else throw e;
|
|
128
|
+
}
|
|
107
129
|
```
|
|
108
130
|
|
|
131
|
+
`executeSwap` (0.40.0; 0.40.2: at most `maxSources` legs, the budget down by one per FILLED leg —
|
|
132
|
+
a refused or unanswered leg does not count, the last leg takes all that remains): ONE swap at a time. First the pass over the swap basket, then ONE wallet
|
|
133
|
+
action stages what `amm-swap` lacks of `quote.stage` (sats only: a plain createAction; a sell's
|
|
134
|
+
tokens: the module transfer). Then legs one at a time: the SERVER's pool list read fresh (0.41.0:
|
|
135
|
+
`GET /@<token>/amm/pools` before EACH leg; the client keeps no list of its own), the engine's
|
|
136
|
+
`nextLeg` over it (`minOut` = the quote's floor less what has filled), the pool's current output by
|
|
137
|
+
its id (`/pools/beef?pool=`), the staged rows that cover the leg (largest first), built, signed,
|
|
138
|
+
relayed; accepted → taken in (payout, own commission, change) before the next leg; refused
|
|
139
|
+
`pool_spent` → the list read again (the relaying host took the validator's state in before it
|
|
140
|
+
answered, 0.41.0); refused otherwise → that pool output excluded; no answer → the overlay
|
|
141
|
+
(a staged input spent: the leg landed), else sent once more, else raced on another pool. It stops
|
|
142
|
+
`filled | cancelled | floor | min | no_pool | fees`. Filled: the last leg's change went to the
|
|
143
|
+
wallet. Stopped early with rows left: `moveBack` runs itself (`result.returned`). Progress phases:
|
|
144
|
+
`staging`, `relaying` / `repricing` (the leg's pool, amounts and the legs filled so far),
|
|
145
|
+
`returning`, `done` / `failed`. The result: `{status, stop, legs: [{poolOutpoint, poolId,
|
|
146
|
+
amountIn, amountOut, txid}], totalIn, totalOut, unfilled, returned?}`.
|
|
147
|
+
|
|
109
148
|
## Build
|
|
110
149
|
|
|
111
150
|
From skein-amm's `web/`: `npm ci` in `ui` and in `engine`, then `npm pack` here (the build
|
package/dist/client.d.ts
CHANGED
|
@@ -15,22 +15,23 @@
|
|
|
15
15
|
* (`hostedTokens`): each token's price, liquidity (TVL) and pool count; no host-wide stream.
|
|
16
16
|
* - **History** (0.39.0, D1–D6): `trades`, `trade`, `candles`, `stats`, `statsAll`, `holders`,
|
|
17
17
|
* `positionsAll` — plain GETs of the history routes (H1–H6, src/lib/overlay.ts).
|
|
18
|
-
* - **Swap** (D11–D16): the token's pools route `GET /@<token>/amm/pools
|
|
19
|
-
* (`
|
|
20
|
-
*
|
|
21
|
-
*
|
|
22
|
-
*
|
|
23
|
-
* /@<token>/amm/pools/beef?
|
|
24
|
-
*
|
|
25
|
-
*
|
|
26
|
-
*
|
|
27
|
-
*
|
|
28
|
-
*
|
|
29
|
-
*
|
|
18
|
+
* - **Swap** (D11–D16; 0.40.0; 0.41.0): the token's pools route `GET /@<token>/amm/pools`, a plain
|
|
19
|
+
* read (`tokenPools`): the pools whose validator is beating and whose commission meets the
|
|
20
|
+
* market's minimum (the host's filter), each validator's minimum leg, the market's commission key
|
|
21
|
+
* hash; a quote is the matching engine's plan over that list (no request); a swap (`executeSwap`)
|
|
22
|
+
* stages what the swap basket lacks by ONE wallet action, then per leg the pools route read fresh,
|
|
23
|
+
* ONE `GET /@<token>/amm/pools/beef?pool=` and the leg's relay request (`amm.swap.submit`, held by
|
|
24
|
+
* the host until the relay rests; 15 s expiry); no answer → the host's `GET /amm/spends`, once
|
|
25
|
+
* more, a race. The pool events (`watchPoolEvents`, 0.41.0: the host's feeds) are signals for
|
|
26
|
+
* display: a page reads the route again on one.
|
|
27
|
+
* - **Liquidity** (D9, D23; 0.40.0: by pool id): the wallet's pool rows and deploy history, then
|
|
28
|
+
* ONE `GET /@<token>/amm/positions?pool=` per token; a deploy the history has but the basket
|
|
29
|
+
* lacks is filed then; Close and Rebalance read their pool's BEEF by its id (`/pools/beef?pool=`);
|
|
30
|
+
* the deploy's terms `GET /@<token>/amm/terms`.
|
|
30
31
|
* - **Your tokens** (D17, D18, D19, D24): the wallet's module and the swap basket; the token list
|
|
31
|
-
* once and ONE discovery `GET /@discovery/1color/tokens?ids=` for held tokens the list lacks;
|
|
32
|
-
*
|
|
33
|
-
* at the host root.
|
|
32
|
+
* once and ONE discovery `GET /@discovery/1color/tokens?ids=` for held tokens the list lacks; the
|
|
33
|
+
* pass over the swap basket (0.40.0: ONE `GET /amm/spends` over every row,
|
|
34
|
+
* src/wallet/swapPayouts.ts); Move back submits at the host root.
|
|
34
35
|
* - **Settings** (D20, D21): the claim card (`claimStatus`: swap's identity, the recipient of
|
|
35
36
|
* root's messages), the token list once, discovery's list and ONE `?ids=` read; Enable's deploy
|
|
36
37
|
* BEEF from the wallet's basket else `GET /@discovery/1color/<token>/deploy`.
|
|
@@ -42,14 +43,13 @@
|
|
|
42
43
|
*/
|
|
43
44
|
import { type WalletInterface } from "@bsv/sdk";
|
|
44
45
|
import { type Send1ColorResult } from "@1sat/actions";
|
|
45
|
-
import { type PoolState, type Plan } from "@dcasegr/amm-engine";
|
|
46
|
-
import { type Candle, type CandleTf, type Holders, type TokenPosition, type TokenStats, type Trade, type TradesPage, type
|
|
47
|
-
import { type Defaults, type Discovery, type EnabledToken, type ListedToken } from "./lib/skein.js";
|
|
46
|
+
import { type Leg, type PoolState, type Plan, type PricePair } from "@dcasegr/amm-engine";
|
|
47
|
+
import { type Candle, type CandleSeries, type CandleTf, type PoolAt, type PoolHistoryPage, type SpendAll, type Holders, type TokenPosition, type TokenStats, type Trade, type TradesPage, type PoolRow, type PoolsAnswer, type PoolEventMessage, type SignedFetch } from "./lib/overlay.js";
|
|
48
|
+
import { type Defaults, type Discovery, type EnabledToken, type ExchangeWallet, type ListedToken } from "./lib/skein.js";
|
|
48
49
|
import type { AuthFetchLike } from "./market/relay.js";
|
|
49
|
-
import { type PreparedSwap } from "./market/swapAction.js";
|
|
50
50
|
import { type MovedBack } from "./market/activeSwap.js";
|
|
51
51
|
import { type PositionRow } from "./lp/positions.js";
|
|
52
|
-
import { ClientError
|
|
52
|
+
import { ClientError } from "./errors.js";
|
|
53
53
|
/** A token id: the BRC-207 assetId `<txid>_<vout>`, `_0` included (src/lib/tokenId.ts). */
|
|
54
54
|
export type TokenId = string;
|
|
55
55
|
/** What a swap of 2% of the price costs: the sats a buy needs to move the marginal price up by `bps`. */
|
|
@@ -64,7 +64,10 @@ export interface HostedToken {
|
|
|
64
64
|
dec: number;
|
|
65
65
|
/** An image URL (a data: URL of the deploy's embedded icon, or an ORDFS URL). */
|
|
66
66
|
icon?: string;
|
|
67
|
-
/**
|
|
67
|
+
/**
|
|
68
|
+
* Sats per whole token (0.40.0: the stats' `price`, the midpoint of what a buy and a sell of 1% of
|
|
69
|
+
* the pooled sats would pay now). Null with no open pool.
|
|
70
|
+
*/
|
|
68
71
|
marginalPrice: number | null;
|
|
69
72
|
depth: Depth | null;
|
|
70
73
|
/** Number of open pools. */
|
|
@@ -81,6 +84,8 @@ export interface HostedToken {
|
|
|
81
84
|
export interface PoolView {
|
|
82
85
|
/** `<txid>.<vout>` */
|
|
83
86
|
outpoint: string;
|
|
87
|
+
/** The pool's id (0.40.0): its deploy outpoint, `<txid>_<vout>`. */
|
|
88
|
+
poolId: string;
|
|
84
89
|
tokenId: TokenId;
|
|
85
90
|
sats: bigint;
|
|
86
91
|
tokens: bigint;
|
|
@@ -99,11 +104,18 @@ export interface QuoteRequest {
|
|
|
99
104
|
amountIn: bigint;
|
|
100
105
|
/** Max slippage against the quoted amount out, basis points. */
|
|
101
106
|
maxSlippageBps: number;
|
|
102
|
-
|
|
107
|
+
/**
|
|
108
|
+
* 0.40.2: the most pools the order may draw on, filled legs counted — a positive integer the
|
|
109
|
+
* caller always gives; the fee sats staged are for exactly that many legs. 1: exactly one leg
|
|
110
|
+
* for the whole amount. Replaces `allowPartial` (`false` was 1).
|
|
111
|
+
*/
|
|
112
|
+
maxSources: number;
|
|
103
113
|
}
|
|
104
114
|
export interface QuoteLeg {
|
|
105
115
|
/** The pool, `<txid>.<vout>`. */
|
|
106
116
|
poolOutpoint: string;
|
|
117
|
+
/** The pool's id (0.40.0). */
|
|
118
|
+
poolId: string;
|
|
107
119
|
amountIn: bigint;
|
|
108
120
|
amountOut: bigint;
|
|
109
121
|
/** Share of the amount in, basis points (the legs sum to 10000). */
|
|
@@ -114,37 +126,64 @@ export interface QuoteLeg {
|
|
|
114
126
|
tokens: bigint;
|
|
115
127
|
};
|
|
116
128
|
validator: ValidatorRef;
|
|
129
|
+
/** The leg's own pool's fees (0.40.0: the fee line per leg). */
|
|
130
|
+
fees: Fees;
|
|
131
|
+
}
|
|
132
|
+
/** What Swap stages into the swap basket before its first leg (0.40.0): the swap amount exact, and the fee sats. */
|
|
133
|
+
export interface QuoteStage {
|
|
134
|
+
/** The swap amount: sats on a buy, token base units on a sell. */
|
|
135
|
+
amount: bigint;
|
|
136
|
+
/** The sats for the carriers and miner fees of `maxSources` legs (0.40.2). */
|
|
137
|
+
feeSats: bigint;
|
|
117
138
|
}
|
|
118
139
|
export interface Quote {
|
|
119
140
|
request: QuoteRequest;
|
|
120
141
|
legs: QuoteLeg[];
|
|
121
142
|
amountOut: bigint;
|
|
122
|
-
/** The least amount out the swap accepts:
|
|
143
|
+
/** The least amount out the swap accepts (the floor): the route's amount out less max slippage. */
|
|
123
144
|
minAmountOut: bigint;
|
|
124
145
|
/** Sats per whole token this swap pays (fees included). */
|
|
125
146
|
effectivePrice: number;
|
|
126
|
-
/**
|
|
147
|
+
/**
|
|
148
|
+
* Sats per whole token now (0.40.0: the engine's `priceOf` over the pools the page holds — what a
|
|
149
|
+
* buy of 1% of the pooled sats would pay on a buy, a sell of 1% of the pooled tokens on a sell).
|
|
150
|
+
*/
|
|
127
151
|
marginalPrice: number;
|
|
128
152
|
/** |effective − marginal| / marginal, basis points. */
|
|
129
153
|
impactBps: number;
|
|
130
|
-
/**
|
|
131
|
-
|
|
154
|
+
/** What Swap stages (0.40.0). */
|
|
155
|
+
stage: QuoteStage;
|
|
156
|
+
/** The miner fee estimate of one leg, sats. */
|
|
157
|
+
legMinerFeeSats: bigint;
|
|
132
158
|
}
|
|
159
|
+
/** One leg of a swap that filled (0.40.0). */
|
|
133
160
|
export interface LegResult {
|
|
161
|
+
/** The pool output it spent, `<txid>.<vout>`. */
|
|
134
162
|
poolOutpoint: string;
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
repriced?: true;
|
|
140
|
-
/** 0.34.0 (D15): no answer yet — the swap's id, for "Check again" (`checkSwapAgain`). */
|
|
141
|
-
checkId?: string;
|
|
142
|
-
/** 0.38.0 (D13): the failure's kind, when it has one (`error` stays the text). */
|
|
143
|
-
kind?: ClientErrorKind;
|
|
163
|
+
poolId: string;
|
|
164
|
+
amountIn: bigint;
|
|
165
|
+
amountOut: bigint;
|
|
166
|
+
txid: string;
|
|
144
167
|
}
|
|
168
|
+
/** Why a swap stopped (0.40.0). */
|
|
169
|
+
export type SwapStop = "filled" | "cancelled" | "floor" | "min" | "no_pool" | "fees";
|
|
145
170
|
export interface SwapResult {
|
|
171
|
+
/** "filled": every unit filled; "partial": some; "failed": none. */
|
|
146
172
|
status: "filled" | "partial" | "failed";
|
|
173
|
+
stop: SwapStop;
|
|
174
|
+
/** The legs that filled, in order. */
|
|
147
175
|
legs: LegResult[];
|
|
176
|
+
totalIn: bigint;
|
|
177
|
+
totalOut: bigint;
|
|
178
|
+
/** The swap amount not filled. */
|
|
179
|
+
unfilled: bigint;
|
|
180
|
+
/** What went back to the wallet when the swap stopped early (the Move back's), or why it did not. */
|
|
181
|
+
returned?: {
|
|
182
|
+
txid: string;
|
|
183
|
+
tokens: bigint;
|
|
184
|
+
} | {
|
|
185
|
+
error: string;
|
|
186
|
+
};
|
|
148
187
|
}
|
|
149
188
|
/** The validator's fees, basis points of the amount in. The LP accepts them; there is no fee input. */
|
|
150
189
|
export interface Fees {
|
|
@@ -172,11 +211,17 @@ export interface ValidatorTerms {
|
|
|
172
211
|
/** "this exchange's" when the validator is this skein. */
|
|
173
212
|
isThisExchange: boolean;
|
|
174
213
|
fees: Fees;
|
|
214
|
+
/** The validator's minimum leg, sats on the leg's sats side (0.40.0; 0: none). */
|
|
215
|
+
minLegSats: number;
|
|
175
216
|
}
|
|
176
217
|
/** One of the user's pools. A position is only deployed or closed (no add, no partial remove). */
|
|
177
218
|
export interface Position {
|
|
178
219
|
/** The pool, `<txid>.<vout>`. */
|
|
179
220
|
outpoint: string;
|
|
221
|
+
/** The pool's id (0.40.0): its deploy outpoint, `<txid>_<vout>`. */
|
|
222
|
+
poolId: string;
|
|
223
|
+
/** The pool's swaps so far. */
|
|
224
|
+
swaps: number;
|
|
180
225
|
tokenId: TokenId;
|
|
181
226
|
sym: string;
|
|
182
227
|
dec: number;
|
|
@@ -244,8 +289,6 @@ export interface WalletToken {
|
|
|
244
289
|
outputs: number;
|
|
245
290
|
/** Held in the exchange's active swap basket (`amm-swap`): spent by swap legs, or moved back. */
|
|
246
291
|
inSwaps: bigint;
|
|
247
|
-
/** Sats staged in `amm-swap` for the token's swap legs (0.29.6): spent by swap legs, or moved back. */
|
|
248
|
-
swapSats: number;
|
|
249
292
|
/** Registered on this exchange. */
|
|
250
293
|
onExchange: boolean;
|
|
251
294
|
}
|
|
@@ -265,9 +308,10 @@ export interface RegisteredToken {
|
|
|
265
308
|
icon?: string;
|
|
266
309
|
status: EnabledToken["status"];
|
|
267
310
|
}
|
|
268
|
-
export type { EnabledToken, Defaults, Discovery, PoolRow, PoolsAnswer, Candle, CandleTf, Holders, TokenPosition, TokenStats, Trade, TradesPage };
|
|
269
|
-
export type {
|
|
270
|
-
export {
|
|
311
|
+
export type { EnabledToken, Defaults, Discovery, ExchangeWallet, PoolRow, PoolsAnswer, Candle, CandleSeries, CandleTf, Holders, PoolAt, PoolHistoryPage, SpendAll, TokenPosition, TokenStats, Trade, TradesPage };
|
|
312
|
+
export type { PoolEvent, PoolEventMessage, PoolRevert } from "./lib/overlay.js";
|
|
313
|
+
export type { Price } from "./lib/overlay.js";
|
|
314
|
+
export { parsePoolEventMessage } from "./lib/overlay.js";
|
|
271
315
|
/** A token's symbol, decimals and icon, read off its deploy output. */
|
|
272
316
|
export interface DeployMeta {
|
|
273
317
|
sym?: string;
|
|
@@ -302,8 +346,19 @@ export declare function hostedFrom(list: EnabledToken[], stats: TokenStats[] | n
|
|
|
302
346
|
export declare function poolViews(answer: PoolsAnswer | null, tokenId: TokenId): PoolView[];
|
|
303
347
|
/** The fees a pool's own record names (D13: the Swap page's fee line), basis points. */
|
|
304
348
|
export declare function poolFees(p: Pick<PoolState, "liquidityFeeBps" | "validationFeeBps" | "commissionBps">): Fees;
|
|
305
|
-
/**
|
|
306
|
-
|
|
349
|
+
/**
|
|
350
|
+
* A pools answer's rows as the planner takes them (0.40.0): each pool with its validator's
|
|
351
|
+
* minimum leg (`validators[].minLegSats`, the validator's announced terms).
|
|
352
|
+
*/
|
|
353
|
+
export declare function poolsWithMinimums(answer: PoolsAnswer): PoolRow[];
|
|
354
|
+
/** Sats per whole token of an exact pair (`sats` per `tokens` base units), 0 when `tokens` is 0. */
|
|
355
|
+
export declare function pairPrice(p: PricePair, dec: number): number;
|
|
356
|
+
/**
|
|
357
|
+
* A leg's sats beyond its amount in (0.40.0, the stage's fee sats): the miner fee estimate plus its
|
|
358
|
+
* 1-sat carriers — on a buy the token payout; on a sell the token fee and commission outputs that
|
|
359
|
+
* are not zero, and the token change.
|
|
360
|
+
*/
|
|
361
|
+
export declare function legCarrySats(leg: Pick<Leg, "liquidityFee" | "validationFee" | "commission">, buy: boolean, minerFeeSats: bigint): bigint;
|
|
307
362
|
/**
|
|
308
363
|
* wallet-toolbox's `specOpWalletBalance` (`sdk.specOpWalletBalance`, @bsv/wallet-toolbox-client): the listOutputs "basket" of its
|
|
309
364
|
* balance special operation. Written out, not imported: the client package exports it only inside its `sdk` namespace, which
|
|
@@ -342,18 +397,17 @@ export interface EnableCandidate {
|
|
|
342
397
|
* instance's list (enabled or disabled) left out. Pure: the reads are `tokensToEnable`'s.
|
|
343
398
|
*/
|
|
344
399
|
export declare function enableCandidates(listed: ListedToken[], walletIds: string[], onList: string[]): EnableCandidate[];
|
|
345
|
-
/** The three fees root sets (basis points, integers 0 to 10 000). */
|
|
400
|
+
/** The three fees root sets (basis points, integers 0 to 10 000), and (0.40.0) the minimum leg in sats (absent or 0: none). */
|
|
346
401
|
export interface TermsInput {
|
|
347
402
|
lpBps: number;
|
|
348
403
|
validatorBps: number;
|
|
349
404
|
commissionBps: number;
|
|
405
|
+
minLegSats?: number;
|
|
350
406
|
}
|
|
351
407
|
/** What a quote was planned from: kept for its execution. */
|
|
352
408
|
interface Planned {
|
|
353
409
|
plan: Plan;
|
|
354
|
-
|
|
355
|
-
live: LiveAnswer;
|
|
356
|
-
market: PoolsAnswer["market"];
|
|
410
|
+
answer: PoolsAnswer;
|
|
357
411
|
dec: number;
|
|
358
412
|
sym: string;
|
|
359
413
|
}
|
|
@@ -378,15 +432,31 @@ export interface ClientOptions {
|
|
|
378
432
|
/** The wallet's identity key, when the caller has it (the claim's check). Default: read from the wallet when needed. */
|
|
379
433
|
identityKey?: string | null;
|
|
380
434
|
}
|
|
381
|
-
/**
|
|
435
|
+
/**
|
|
436
|
+
* Where a swap is (`executeSwap`'s `onProgress`, D12; 0.40.0): `staging` (what the swap basket
|
|
437
|
+
* lacks is staged), `relaying` (a leg sent: its pool outpoint `<txid>.<vout>` and amounts, and the
|
|
438
|
+
* legs filled so far), `repricing` (a leg refused `pool_spent`, the pool's row replaced),
|
|
439
|
+
* `returning` (a swap that stopped early moves its rows back), then `done` or `failed`.
|
|
440
|
+
*/
|
|
382
441
|
export type SwapProgress = {
|
|
383
442
|
phase: "staging";
|
|
443
|
+
sats: bigint;
|
|
444
|
+
tokens: bigint;
|
|
384
445
|
} | {
|
|
385
446
|
phase: "relaying";
|
|
386
447
|
leg: string;
|
|
448
|
+
amountIn: bigint;
|
|
449
|
+
amountOut: bigint;
|
|
450
|
+
filled: LegResult[];
|
|
387
451
|
} | {
|
|
388
452
|
phase: "repricing";
|
|
389
453
|
leg: string;
|
|
454
|
+
amountIn: bigint;
|
|
455
|
+
amountOut: bigint;
|
|
456
|
+
filled: LegResult[];
|
|
457
|
+
} | {
|
|
458
|
+
phase: "returning";
|
|
459
|
+
filled: LegResult[];
|
|
390
460
|
} | {
|
|
391
461
|
phase: "done";
|
|
392
462
|
result: SwapResult;
|
|
@@ -396,8 +466,10 @@ export type SwapProgress = {
|
|
|
396
466
|
error?: ClientError | Error;
|
|
397
467
|
};
|
|
398
468
|
export interface SwapOptions {
|
|
399
|
-
/** Called as the swap moves (
|
|
469
|
+
/** Called as the swap moves (see `SwapProgress`). */
|
|
400
470
|
onProgress?: (p: SwapProgress) => void;
|
|
471
|
+
/** Aborted: the swap stops before its next leg (`cancelled`). */
|
|
472
|
+
signal?: AbortSignal;
|
|
401
473
|
}
|
|
402
474
|
/** What a client remembers between calls; shared by `withWallet`'s clients. */
|
|
403
475
|
interface Shared {
|
|
@@ -407,12 +479,8 @@ interface Shared {
|
|
|
407
479
|
claimRead: ClaimStatus | null;
|
|
408
480
|
/** What each quote was planned from: kept for its execution. */
|
|
409
481
|
planned: WeakMap<Quote, Planned>;
|
|
410
|
-
/**
|
|
411
|
-
|
|
412
|
-
prepared: PreparedSwap;
|
|
413
|
-
base: string;
|
|
414
|
-
af: Signed;
|
|
415
|
-
}>;
|
|
482
|
+
/** A swap is running (0.40.0: one at a time). */
|
|
483
|
+
swapping: boolean;
|
|
416
484
|
/** The positions last loaded, by the output a Close acts on (`<txid>.<vout>`): the wallet's row (its LP key) and the token. */
|
|
417
485
|
loaded: Map<string, PositionRow>;
|
|
418
486
|
/** `onDataChange`'s listeners. */
|
|
@@ -450,36 +518,47 @@ declare function makeClient(opts: ClientOptions, s: Shared): {
|
|
|
450
518
|
isRoot: (identityKey: string | null) => Promise<boolean>;
|
|
451
519
|
claimExchange: () => Promise<boolean>;
|
|
452
520
|
hostedTokens: () => Promise<HostedToken[]>;
|
|
453
|
-
|
|
521
|
+
tokenPools: (tokenId: string) => Promise<PoolsAnswer>;
|
|
522
|
+
watchPoolEvents: (tokenId: TokenId | "all", onEvent: (e: PoolEventMessage) => void, onError?: (e: unknown) => void) => () => void;
|
|
454
523
|
trades: (tokenId: string, o?: {
|
|
455
524
|
from?: number;
|
|
456
525
|
to?: number;
|
|
457
526
|
limit?: number;
|
|
458
527
|
before?: string;
|
|
459
|
-
|
|
528
|
+
pool?: string;
|
|
460
529
|
} | undefined) => Promise<TradesPage>;
|
|
461
530
|
trade: (tokenId: string, txid: string) => Promise<Trade | null>;
|
|
462
531
|
candles: (tokenId: string, o: {
|
|
463
532
|
tf: CandleTf;
|
|
464
533
|
from: number;
|
|
465
534
|
to: number;
|
|
535
|
+
series?: CandleSeries;
|
|
466
536
|
}) => Promise<Candle[]>;
|
|
537
|
+
poolsAt: (tokenId: string, t: number) => Promise<PoolAt[]>;
|
|
538
|
+
poolHistory: (tokenId: string, o?: {
|
|
539
|
+
from?: number;
|
|
540
|
+
to?: number;
|
|
541
|
+
pool?: string;
|
|
542
|
+
limit?: number;
|
|
543
|
+
after?: string;
|
|
544
|
+
} | undefined) => Promise<PoolHistoryPage>;
|
|
545
|
+
spendsAll: (outpoints: string[]) => Promise<SpendAll[]>;
|
|
467
546
|
stats: (tokenId: string) => Promise<TokenStats>;
|
|
468
547
|
statsAll: (o?: {
|
|
469
548
|
ids?: TokenId[];
|
|
549
|
+
fresh?: boolean;
|
|
470
550
|
} | undefined) => Promise<TokenStats[]>;
|
|
471
551
|
holders: (tokenId: string, o?: {
|
|
472
552
|
limit?: number;
|
|
473
553
|
skip?: number;
|
|
474
554
|
} | undefined) => Promise<Holders>;
|
|
475
|
-
positionsAll: (
|
|
555
|
+
positionsAll: (poolIds: string[]) => Promise<TokenPosition[]>;
|
|
476
556
|
registeredTokens: () => Promise<RegisteredToken[]>;
|
|
477
557
|
quoteSwap: (req: QuoteRequest, held: PoolsAnswer | null, meta: {
|
|
478
558
|
sym: string;
|
|
479
559
|
dec: number;
|
|
480
560
|
}) => Quote;
|
|
481
561
|
executeSwap: (quote: Quote, o?: SwapOptions) => Promise<SwapResult>;
|
|
482
|
-
checkSwapAgain: (leg: LegResult) => Promise<LegResult>;
|
|
483
562
|
walletSats: () => Promise<bigint>;
|
|
484
563
|
myPositions: () => Promise<Position[]>;
|
|
485
564
|
validatorTerms: (tokenId: string) => Promise<NoTerms | ValidatorTerms>;
|
|
@@ -488,6 +567,8 @@ declare function makeClient(opts: ClientOptions, s: Shared): {
|
|
|
488
567
|
rebalancePosition: (req: RebalanceRequest) => Promise<RebalanceResult>;
|
|
489
568
|
myTokens: () => Promise<WalletToken[]>;
|
|
490
569
|
settleSwaps: () => Promise<string[]>;
|
|
570
|
+
swapBasketSats: () => Promise<number>;
|
|
571
|
+
moveBackStagedSats: () => Promise<MovedBack>;
|
|
491
572
|
moveBackTokens: (tokenId: string) => Promise<MovedBack>;
|
|
492
573
|
sendTokens: (tokenId: string, handle: string, amount: bigint, memo?: string | undefined) => Promise<Send1ColorResult>;
|
|
493
574
|
deployBeef: (tokenId: string, wallet?: WalletInterface | null | undefined) => Promise<DeployFound>;
|
|
@@ -502,6 +583,7 @@ declare function makeClient(opts: ClientOptions, s: Shared): {
|
|
|
502
583
|
lpFeeBps: number;
|
|
503
584
|
validatorFeeBps: number;
|
|
504
585
|
commissionBps: number;
|
|
586
|
+
minLegSats: number;
|
|
505
587
|
} | null>;
|
|
506
588
|
setTokenTerms: (tokenId: string, t: TermsInput | null) => Promise<void>;
|
|
507
589
|
clearDefaultTerms: () => Promise<void>;
|
|
@@ -509,6 +591,22 @@ declare function makeClient(opts: ClientOptions, s: Shared): {
|
|
|
509
591
|
clearDefaultMarket: () => Promise<void>;
|
|
510
592
|
discoveryState: () => Promise<Discovery>;
|
|
511
593
|
setDiscovery: (on: boolean) => Promise<void>;
|
|
594
|
+
setEnablePrice: (sats: number | null) => Promise<void>;
|
|
595
|
+
exchangeWallet: () => Promise<ExchangeWallet>;
|
|
596
|
+
withdrawAll: () => Promise<{
|
|
597
|
+
n: number;
|
|
598
|
+
txid: string;
|
|
599
|
+
sats: number;
|
|
600
|
+
at: number;
|
|
601
|
+
outputIndex: number;
|
|
602
|
+
derivationPrefix: string;
|
|
603
|
+
derivationSuffix: string;
|
|
604
|
+
senderIdentityKey: string;
|
|
605
|
+
}>;
|
|
606
|
+
enableTokenPaid: (tokenId: string, o?: {
|
|
607
|
+
deployBeef?: number[];
|
|
608
|
+
} | undefined) => Promise<EnabledToken & Record<string, unknown>>;
|
|
609
|
+
settleWithdrawals: () => Promise<string[]>;
|
|
512
610
|
};
|
|
513
611
|
onDataChange: (fn: () => void) => () => void;
|
|
514
612
|
forgetReads: () => void;
|
|
@@ -520,36 +618,47 @@ declare function makeClient(opts: ClientOptions, s: Shared): {
|
|
|
520
618
|
isRoot: (identityKey: string | null) => Promise<boolean>;
|
|
521
619
|
claimExchange: () => Promise<boolean>;
|
|
522
620
|
hostedTokens: () => Promise<HostedToken[]>;
|
|
523
|
-
|
|
621
|
+
tokenPools: (tokenId: string) => Promise<PoolsAnswer>;
|
|
622
|
+
watchPoolEvents: (tokenId: TokenId | "all", onEvent: (e: PoolEventMessage) => void, onError?: (e: unknown) => void) => () => void;
|
|
524
623
|
trades: (tokenId: string, o?: {
|
|
525
624
|
from?: number;
|
|
526
625
|
to?: number;
|
|
527
626
|
limit?: number;
|
|
528
627
|
before?: string;
|
|
529
|
-
|
|
628
|
+
pool?: string;
|
|
530
629
|
} | undefined) => Promise<TradesPage>;
|
|
531
630
|
trade: (tokenId: string, txid: string) => Promise<Trade | null>;
|
|
532
631
|
candles: (tokenId: string, o: {
|
|
533
632
|
tf: CandleTf;
|
|
534
633
|
from: number;
|
|
535
634
|
to: number;
|
|
635
|
+
series?: CandleSeries;
|
|
536
636
|
}) => Promise<Candle[]>;
|
|
637
|
+
poolsAt: (tokenId: string, t: number) => Promise<PoolAt[]>;
|
|
638
|
+
poolHistory: (tokenId: string, o?: {
|
|
639
|
+
from?: number;
|
|
640
|
+
to?: number;
|
|
641
|
+
pool?: string;
|
|
642
|
+
limit?: number;
|
|
643
|
+
after?: string;
|
|
644
|
+
} | undefined) => Promise<PoolHistoryPage>;
|
|
645
|
+
spendsAll: (outpoints: string[]) => Promise<SpendAll[]>;
|
|
537
646
|
stats: (tokenId: string) => Promise<TokenStats>;
|
|
538
647
|
statsAll: (o?: {
|
|
539
648
|
ids?: TokenId[];
|
|
649
|
+
fresh?: boolean;
|
|
540
650
|
} | undefined) => Promise<TokenStats[]>;
|
|
541
651
|
holders: (tokenId: string, o?: {
|
|
542
652
|
limit?: number;
|
|
543
653
|
skip?: number;
|
|
544
654
|
} | undefined) => Promise<Holders>;
|
|
545
|
-
positionsAll: (
|
|
655
|
+
positionsAll: (poolIds: string[]) => Promise<TokenPosition[]>;
|
|
546
656
|
registeredTokens: () => Promise<RegisteredToken[]>;
|
|
547
657
|
quoteSwap: (req: QuoteRequest, held: PoolsAnswer | null, meta: {
|
|
548
658
|
sym: string;
|
|
549
659
|
dec: number;
|
|
550
660
|
}) => Quote;
|
|
551
661
|
executeSwap: (quote: Quote, o?: SwapOptions) => Promise<SwapResult>;
|
|
552
|
-
checkSwapAgain: (leg: LegResult) => Promise<LegResult>;
|
|
553
662
|
walletSats: () => Promise<bigint>;
|
|
554
663
|
myPositions: () => Promise<Position[]>;
|
|
555
664
|
validatorTerms: (tokenId: string) => Promise<NoTerms | ValidatorTerms>;
|
|
@@ -558,6 +667,8 @@ declare function makeClient(opts: ClientOptions, s: Shared): {
|
|
|
558
667
|
rebalancePosition: (req: RebalanceRequest) => Promise<RebalanceResult>;
|
|
559
668
|
myTokens: () => Promise<WalletToken[]>;
|
|
560
669
|
settleSwaps: () => Promise<string[]>;
|
|
670
|
+
swapBasketSats: () => Promise<number>;
|
|
671
|
+
moveBackStagedSats: () => Promise<MovedBack>;
|
|
561
672
|
moveBackTokens: (tokenId: string) => Promise<MovedBack>;
|
|
562
673
|
sendTokens: (tokenId: string, handle: string, amount: bigint, memo?: string | undefined) => Promise<Send1ColorResult>;
|
|
563
674
|
deployBeef: (tokenId: string, wallet?: WalletInterface | null | undefined) => Promise<DeployFound>;
|
|
@@ -572,6 +683,7 @@ declare function makeClient(opts: ClientOptions, s: Shared): {
|
|
|
572
683
|
lpFeeBps: number;
|
|
573
684
|
validatorFeeBps: number;
|
|
574
685
|
commissionBps: number;
|
|
686
|
+
minLegSats: number;
|
|
575
687
|
} | null>;
|
|
576
688
|
setTokenTerms: (tokenId: string, t: TermsInput | null) => Promise<void>;
|
|
577
689
|
clearDefaultTerms: () => Promise<void>;
|
|
@@ -579,4 +691,20 @@ declare function makeClient(opts: ClientOptions, s: Shared): {
|
|
|
579
691
|
clearDefaultMarket: () => Promise<void>;
|
|
580
692
|
discoveryState: () => Promise<Discovery>;
|
|
581
693
|
setDiscovery: (on: boolean) => Promise<void>;
|
|
694
|
+
setEnablePrice: (sats: number | null) => Promise<void>;
|
|
695
|
+
exchangeWallet: () => Promise<ExchangeWallet>;
|
|
696
|
+
withdrawAll: () => Promise<{
|
|
697
|
+
n: number;
|
|
698
|
+
txid: string;
|
|
699
|
+
sats: number;
|
|
700
|
+
at: number;
|
|
701
|
+
outputIndex: number;
|
|
702
|
+
derivationPrefix: string;
|
|
703
|
+
derivationSuffix: string;
|
|
704
|
+
senderIdentityKey: string;
|
|
705
|
+
}>;
|
|
706
|
+
enableTokenPaid: (tokenId: string, o?: {
|
|
707
|
+
deployBeef?: number[];
|
|
708
|
+
} | undefined) => Promise<EnabledToken & Record<string, unknown>>;
|
|
709
|
+
settleWithdrawals: () => Promise<string[]>;
|
|
582
710
|
};
|