@coffer_so/sdk 1.0.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/LICENSE +21 -0
- package/README.md +283 -0
- package/dist/clients/AdminClient.d.ts +194 -0
- package/dist/clients/AdminClient.d.ts.map +1 -0
- package/dist/clients/AdminClient.js +482 -0
- package/dist/clients/AdminClient.js.map +1 -0
- package/dist/clients/CofferBackendClient.d.ts +877 -0
- package/dist/clients/CofferBackendClient.d.ts.map +1 -0
- package/dist/clients/CofferBackendClient.js +536 -0
- package/dist/clients/CofferBackendClient.js.map +1 -0
- package/dist/clients/CubeBackendClient.d.ts +877 -0
- package/dist/clients/CubeBackendClient.d.ts.map +1 -0
- package/dist/clients/CubeBackendClient.js +536 -0
- package/dist/clients/CubeBackendClient.js.map +1 -0
- package/dist/clients/CubicPoolClient.d.ts +120 -0
- package/dist/clients/CubicPoolClient.d.ts.map +1 -0
- package/dist/clients/CubicPoolClient.js +687 -0
- package/dist/clients/CubicPoolClient.js.map +1 -0
- package/dist/clients/PoolFactoryClient.d.ts +53 -0
- package/dist/clients/PoolFactoryClient.d.ts.map +1 -0
- package/dist/clients/PoolFactoryClient.js +91 -0
- package/dist/clients/PoolFactoryClient.js.map +1 -0
- package/dist/clients/RpcClient.d.ts +49 -0
- package/dist/clients/RpcClient.d.ts.map +1 -0
- package/dist/clients/RpcClient.js +135 -0
- package/dist/clients/RpcClient.js.map +1 -0
- package/dist/clients/SingleTokenDepositClient.d.ts +67 -0
- package/dist/clients/SingleTokenDepositClient.d.ts.map +1 -0
- package/dist/clients/SingleTokenDepositClient.js +105 -0
- package/dist/clients/SingleTokenDepositClient.js.map +1 -0
- package/dist/clients/contract-instructions.d.ts +24 -0
- package/dist/clients/contract-instructions.d.ts.map +1 -0
- package/dist/clients/contract-instructions.js +130 -0
- package/dist/clients/contract-instructions.js.map +1 -0
- package/dist/clients/index.d.ts +10 -0
- package/dist/clients/index.d.ts.map +1 -0
- package/dist/clients/index.js +26 -0
- package/dist/clients/index.js.map +1 -0
- package/dist/clients/quote-math.d.ts +15 -0
- package/dist/clients/quote-math.d.ts.map +1 -0
- package/dist/clients/quote-math.js +98 -0
- package/dist/clients/quote-math.js.map +1 -0
- package/dist/clients/tx-builders.d.ts +231 -0
- package/dist/clients/tx-builders.d.ts.map +1 -0
- package/dist/clients/tx-builders.js +861 -0
- package/dist/clients/tx-builders.js.map +1 -0
- package/dist/clients/versioned.d.ts +34 -0
- package/dist/clients/versioned.d.ts.map +1 -0
- package/dist/clients/versioned.js +55 -0
- package/dist/clients/versioned.js.map +1 -0
- package/dist/config/index.d.ts +65 -0
- package/dist/config/index.d.ts.map +1 -0
- package/dist/config/index.js +75 -0
- package/dist/config/index.js.map +1 -0
- package/dist/config/networks.d.ts +12 -0
- package/dist/config/networks.d.ts.map +1 -0
- package/dist/config/networks.js +51 -0
- package/dist/config/networks.js.map +1 -0
- package/dist/config/tokens.d.ts +19 -0
- package/dist/config/tokens.d.ts.map +1 -0
- package/dist/config/tokens.js +43 -0
- package/dist/config/tokens.js.map +1 -0
- package/dist/idl/cubic_pool.json +4203 -0
- package/dist/idl/index.d.ts +1769 -0
- package/dist/idl/index.d.ts.map +1 -0
- package/dist/idl/index.js +18 -0
- package/dist/idl/index.js.map +1 -0
- package/dist/idl/protocol_admin.json +2615 -0
- package/dist/idl/single_token_liquidity.json +1121 -0
- package/dist/index.d.ts +75 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +206 -0
- package/dist/index.js.map +1 -0
- package/dist/math/cubicMath.d.ts +40 -0
- package/dist/math/cubicMath.d.ts.map +1 -0
- package/dist/math/cubicMath.js +82 -0
- package/dist/math/cubicMath.js.map +1 -0
- package/dist/math/fixedPoint.d.ts +19 -0
- package/dist/math/fixedPoint.d.ts.map +1 -0
- package/dist/math/fixedPoint.js +86 -0
- package/dist/math/fixedPoint.js.map +1 -0
- package/dist/math/index.d.ts +9 -0
- package/dist/math/index.d.ts.map +1 -0
- package/dist/math/index.js +30 -0
- package/dist/math/index.js.map +1 -0
- package/dist/math/logExp.d.ts +6 -0
- package/dist/math/logExp.d.ts.map +1 -0
- package/dist/math/logExp.js +68 -0
- package/dist/math/logExp.js.map +1 -0
- package/dist/math/lpLoss.d.ts +44 -0
- package/dist/math/lpLoss.d.ts.map +1 -0
- package/dist/math/lpLoss.js +103 -0
- package/dist/math/lpLoss.js.map +1 -0
- package/dist/math/maxSelloff.d.ts +164 -0
- package/dist/math/maxSelloff.d.ts.map +1 -0
- package/dist/math/maxSelloff.js +397 -0
- package/dist/math/maxSelloff.js.map +1 -0
- package/dist/math/singleToken.d.ts +54 -0
- package/dist/math/singleToken.d.ts.map +1 -0
- package/dist/math/singleToken.js +188 -0
- package/dist/math/singleToken.js.map +1 -0
- package/dist/math/slippage.d.ts +13 -0
- package/dist/math/slippage.d.ts.map +1 -0
- package/dist/math/slippage.js +44 -0
- package/dist/math/slippage.js.map +1 -0
- package/dist/math/surgeFee.d.ts +24 -0
- package/dist/math/surgeFee.d.ts.map +1 -0
- package/dist/math/surgeFee.js +85 -0
- package/dist/math/surgeFee.js.map +1 -0
- package/dist/math/weightedMath.d.ts +20 -0
- package/dist/math/weightedMath.d.ts.map +1 -0
- package/dist/math/weightedMath.js +66 -0
- package/dist/math/weightedMath.js.map +1 -0
- package/dist/parsers/borsh.d.ts +28 -0
- package/dist/parsers/borsh.d.ts.map +1 -0
- package/dist/parsers/borsh.js +104 -0
- package/dist/parsers/borsh.js.map +1 -0
- package/dist/parsers/contracts.d.ts +26 -0
- package/dist/parsers/contracts.d.ts.map +1 -0
- package/dist/parsers/contracts.js +62 -0
- package/dist/parsers/contracts.js.map +1 -0
- package/dist/parsers/events.d.ts +3 -0
- package/dist/parsers/events.d.ts.map +1 -0
- package/dist/parsers/events.js +281 -0
- package/dist/parsers/events.js.map +1 -0
- package/dist/parsers/index.d.ts +6 -0
- package/dist/parsers/index.d.ts.map +1 -0
- package/dist/parsers/index.js +22 -0
- package/dist/parsers/index.js.map +1 -0
- package/dist/parsers/mintAccount.d.ts +24 -0
- package/dist/parsers/mintAccount.d.ts.map +1 -0
- package/dist/parsers/mintAccount.js +27 -0
- package/dist/parsers/mintAccount.js.map +1 -0
- package/dist/parsers/poolAccount.d.ts +141 -0
- package/dist/parsers/poolAccount.d.ts.map +1 -0
- package/dist/parsers/poolAccount.js +224 -0
- package/dist/parsers/poolAccount.js.map +1 -0
- package/dist/types/contracts.d.ts +1340 -0
- package/dist/types/contracts.d.ts.map +1 -0
- package/dist/types/contracts.js +3 -0
- package/dist/types/contracts.js.map +1 -0
- package/dist/types/events.d.ts +172 -0
- package/dist/types/events.d.ts.map +1 -0
- package/dist/types/events.js +3 -0
- package/dist/types/events.js.map +1 -0
- package/dist/types/index.d.ts +6 -0
- package/dist/types/index.d.ts.map +1 -0
- package/dist/types/index.js +22 -0
- package/dist/types/index.js.map +1 -0
- package/dist/types/pool.d.ts +149 -0
- package/dist/types/pool.d.ts.map +1 -0
- package/dist/types/pool.js +3 -0
- package/dist/types/pool.js.map +1 -0
- package/dist/types/result.d.ts +24 -0
- package/dist/types/result.d.ts.map +1 -0
- package/dist/types/result.js +11 -0
- package/dist/types/result.js.map +1 -0
- package/dist/types/tx.d.ts +261 -0
- package/dist/types/tx.d.ts.map +1 -0
- package/dist/types/tx.js +3 -0
- package/dist/types/tx.js.map +1 -0
- package/dist/utils/errors.d.ts +44 -0
- package/dist/utils/errors.d.ts.map +1 -0
- package/dist/utils/errors.js +192 -0
- package/dist/utils/errors.js.map +1 -0
- package/dist/utils/extensions.d.ts +98 -0
- package/dist/utils/extensions.d.ts.map +1 -0
- package/dist/utils/extensions.js +187 -0
- package/dist/utils/extensions.js.map +1 -0
- package/dist/utils/index.d.ts +5 -0
- package/dist/utils/index.d.ts.map +1 -0
- package/dist/utils/index.js +21 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/utils/pda.d.ts +8 -0
- package/dist/utils/pda.d.ts.map +1 -0
- package/dist/utils/pda.js +27 -0
- package/dist/utils/pda.js.map +1 -0
- package/dist/utils/retry.d.ts +22 -0
- package/dist/utils/retry.d.ts.map +1 -0
- package/dist/utils/retry.js +62 -0
- package/dist/utils/retry.js.map +1 -0
- package/package.json +54 -0
- package/src/clients/AdminClient.ts +608 -0
- package/src/clients/CofferBackendClient.ts +1413 -0
- package/src/clients/CubicPoolClient.ts +719 -0
- package/src/clients/PoolFactoryClient.ts +110 -0
- package/src/clients/RpcClient.ts +195 -0
- package/src/clients/SingleTokenDepositClient.ts +143 -0
- package/src/clients/contract-instructions.ts +115 -0
- package/src/clients/index.ts +9 -0
- package/src/clients/quote-math.ts +81 -0
- package/src/clients/tx-builders.ts +1096 -0
- package/src/clients/versioned.ts +80 -0
- package/src/config/index.ts +111 -0
- package/src/config/networks.ts +71 -0
- package/src/config/tokens.ts +52 -0
- package/src/idl/cubic_pool.json +4203 -0
- package/src/idl/index.ts +13 -0
- package/src/idl/protocol_admin.json +2615 -0
- package/src/idl/single_token_liquidity.json +1121 -0
- package/src/index.ts +262 -0
- package/src/math/cubicMath.ts +92 -0
- package/src/math/fixedPoint.ts +71 -0
- package/src/math/index.ts +13 -0
- package/src/math/logExp.ts +61 -0
- package/src/math/lpLoss.ts +160 -0
- package/src/math/maxSelloff.ts +564 -0
- package/src/math/singleToken.ts +251 -0
- package/src/math/slippage.ts +38 -0
- package/src/math/surgeFee.ts +101 -0
- package/src/math/weightedMath.ts +64 -0
- package/src/parsers/borsh.ts +106 -0
- package/src/parsers/contracts.ts +64 -0
- package/src/parsers/events.ts +275 -0
- package/src/parsers/index.ts +5 -0
- package/src/parsers/mintAccount.ts +44 -0
- package/src/parsers/poolAccount.ts +372 -0
- package/src/types/contracts.ts +238 -0
- package/src/types/events.ts +198 -0
- package/src/types/index.ts +5 -0
- package/src/types/pool.ts +147 -0
- package/src/types/result.ts +51 -0
- package/src/types/tx.ts +278 -0
- package/src/utils/errors.ts +210 -0
- package/src/utils/extensions.ts +196 -0
- package/src/utils/index.ts +4 -0
- package/src/utils/pda.ts +58 -0
- package/src/utils/retry.ts +85 -0
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
14
|
+
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
|
+
};
|
|
16
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
|
+
__exportStar(require("./fixedPoint"), exports);
|
|
18
|
+
__exportStar(require("./logExp"), exports);
|
|
19
|
+
__exportStar(require("./cubicMath"), exports);
|
|
20
|
+
__exportStar(require("./weightedMath"), exports);
|
|
21
|
+
__exportStar(require("./singleToken"), exports);
|
|
22
|
+
__exportStar(require("./slippage"), exports);
|
|
23
|
+
__exportStar(require("./maxSelloff"), exports);
|
|
24
|
+
__exportStar(require("./lpLoss"), exports);
|
|
25
|
+
// NOTE: "./surgeFee" is deliberately NOT star-exported — its
|
|
26
|
+
// calcSurgeFeePct/calcSurgeFeeAmount would shadow the same-named maxSelloff
|
|
27
|
+
// exports (an ambiguous star re-export silently drops the name, breaking
|
|
28
|
+
// existing consumers). The quote engine imports it by path; only the
|
|
29
|
+
// SurgeCurve type is re-exported from the package root.
|
|
30
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/math/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,+CAA6B;AAC7B,2CAAyB;AACzB,8CAA4B;AAC5B,iDAA+B;AAC/B,gDAA8B;AAC9B,6CAA2B;AAC3B,+CAA6B;AAC7B,2CAAyB;AACzB,6DAA6D;AAC7D,4EAA4E;AAC5E,yEAAyE;AACzE,qEAAqE;AACrE,wDAAwD"}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
export declare const MAX_NATURAL_EXPONENT = 46000000000000000000n;
|
|
2
|
+
export declare const MIN_NATURAL_EXPONENT = -41000000000000000000n;
|
|
3
|
+
export declare function lnFp(a: bigint): bigint;
|
|
4
|
+
export declare function expFp(x: bigint): bigint;
|
|
5
|
+
export declare function powFp(base: bigint, exponent: bigint): bigint;
|
|
6
|
+
//# sourceMappingURL=logExp.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"logExp.d.ts","sourceRoot":"","sources":["../../src/math/logExp.ts"],"names":[],"mappings":"AAEA,eAAO,MAAM,oBAAoB,wBAAwB,CAAC;AAC1D,eAAO,MAAM,oBAAoB,yBAAyB,CAAC;AAmB3D,wBAAgB,IAAI,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM,CAKtC;AACD,wBAAgB,KAAK,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM,CAkBvC;AACD,wBAAgB,KAAK,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,MAAM,CAa5D"}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.MIN_NATURAL_EXPONENT = exports.MAX_NATURAL_EXPONENT = void 0;
|
|
4
|
+
exports.lnFp = lnFp;
|
|
5
|
+
exports.expFp = expFp;
|
|
6
|
+
exports.powFp = powFp;
|
|
7
|
+
/** Exact integer port of cubic-pool log_exp_math.rs (audit-fixes-excluded-SF). */
|
|
8
|
+
const fixedPoint_1 = require("./fixedPoint");
|
|
9
|
+
exports.MAX_NATURAL_EXPONENT = 46000000000000000000n;
|
|
10
|
+
exports.MIN_NATURAL_EXPONENT = -41000000000000000000n;
|
|
11
|
+
const X = [32000000000000000000n, 16000000000000000000n, 8000000000000000000n, 4000000000000000000n, 2000000000000000000n, 1000000000000000000n, 500000000000000000n, 250000000000000000n, 125000000000000000n, 62500000000000000n];
|
|
12
|
+
const A = [78962960182680695161000000000000n, 8886110520507872636760000n, 2980957987041728274740n, 54598150033144239078n, 7389056098930650227n, 2718281828459045235n, 1648721270700128146n, 1284025416687741484n, 1133148453066826316n, 1064494458917859429n];
|
|
13
|
+
function lnPositive(a) {
|
|
14
|
+
let sum = 0n;
|
|
15
|
+
for (let i = 0; i < X.length; i++)
|
|
16
|
+
if (a >= A[i]) {
|
|
17
|
+
a = (0, fixedPoint_1.mulDivDown)(a, fixedPoint_1.ONE, A[i]);
|
|
18
|
+
sum += X[i];
|
|
19
|
+
}
|
|
20
|
+
const z = (0, fixedPoint_1.mulDivDown)(a - fixedPoint_1.ONE, fixedPoint_1.ONE, (0, fixedPoint_1.assertU128)(a + fixedPoint_1.ONE));
|
|
21
|
+
const zSq = (0, fixedPoint_1.assertI128)(z * z) / fixedPoint_1.ONE;
|
|
22
|
+
let num = z, seriesSum = z;
|
|
23
|
+
for (let k = 1n; k < 6n; k++) {
|
|
24
|
+
num = (0, fixedPoint_1.assertI128)(num * zSq) / fixedPoint_1.ONE;
|
|
25
|
+
seriesSum = (0, fixedPoint_1.assertI128)(seriesSum + num / (2n * k + 1n));
|
|
26
|
+
}
|
|
27
|
+
return (0, fixedPoint_1.assertI128)(sum + (0, fixedPoint_1.assertI128)(seriesSum * 2n));
|
|
28
|
+
}
|
|
29
|
+
function lnFp(a) {
|
|
30
|
+
(0, fixedPoint_1.assertU128)(a);
|
|
31
|
+
if (a === 0n)
|
|
32
|
+
throw new Error("logExp.ln: divide by zero");
|
|
33
|
+
return a < fixedPoint_1.ONE ? -lnPositive((0, fixedPoint_1.mulDivDown)(fixedPoint_1.ONE, fixedPoint_1.ONE, a)) : lnPositive(a);
|
|
34
|
+
}
|
|
35
|
+
function expFp(x) {
|
|
36
|
+
(0, fixedPoint_1.assertI128)(x);
|
|
37
|
+
if (x < exports.MIN_NATURAL_EXPONENT || x > exports.MAX_NATURAL_EXPONENT)
|
|
38
|
+
throw new Error("logExp.exp: exponent out of range");
|
|
39
|
+
if (x < 0n)
|
|
40
|
+
return (0, fixedPoint_1.mulDivDown)(fixedPoint_1.ONE, fixedPoint_1.ONE, expFp(-x));
|
|
41
|
+
let product = fixedPoint_1.ONE;
|
|
42
|
+
for (let i = 0; i < X.length; i++)
|
|
43
|
+
if (x >= X[i]) {
|
|
44
|
+
x -= X[i];
|
|
45
|
+
product = (0, fixedPoint_1.mulDivDown)(product, A[i], fixedPoint_1.ONE);
|
|
46
|
+
}
|
|
47
|
+
let sum = (0, fixedPoint_1.assertU128)(fixedPoint_1.ONE + x), term = x;
|
|
48
|
+
for (let n = 2n; n <= 12n; n++) {
|
|
49
|
+
term = (0, fixedPoint_1.mulDivDown)(term, x, fixedPoint_1.ONE) / n;
|
|
50
|
+
sum = (0, fixedPoint_1.assertU128)(sum + term);
|
|
51
|
+
}
|
|
52
|
+
return (0, fixedPoint_1.mulDivDown)(product, sum, fixedPoint_1.ONE);
|
|
53
|
+
}
|
|
54
|
+
function powFp(base, exponent) {
|
|
55
|
+
(0, fixedPoint_1.assertU128)(base);
|
|
56
|
+
(0, fixedPoint_1.assertU128)(exponent);
|
|
57
|
+
if (exponent === 0n || base === fixedPoint_1.ONE)
|
|
58
|
+
return fixedPoint_1.ONE;
|
|
59
|
+
if (base === 0n)
|
|
60
|
+
return 0n;
|
|
61
|
+
const logarithm = lnFp(base);
|
|
62
|
+
// Rust casts u128 to i128 here. Valid pool weights are far below i128::MAX.
|
|
63
|
+
const y = BigInt.asIntN(128, exponent);
|
|
64
|
+
const whole = (0, fixedPoint_1.assertI128)((logarithm / fixedPoint_1.ONE) * y);
|
|
65
|
+
const fraction = (0, fixedPoint_1.assertI128)((logarithm % fixedPoint_1.ONE) * y) / fixedPoint_1.ONE;
|
|
66
|
+
return expFp((0, fixedPoint_1.assertI128)(whole + fraction));
|
|
67
|
+
}
|
|
68
|
+
//# sourceMappingURL=logExp.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"logExp.js","sourceRoot":"","sources":["../../src/math/logExp.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
export interface PredictLpLossParams {
|
|
2
|
+
/** Normalized weights in bps (sum = WEIGHT_SCALE). */
|
|
3
|
+
weightsBps: number[];
|
|
4
|
+
virtualBalances: bigint[];
|
|
5
|
+
/** LP-accessible balances: actual − protocolFeesOwed. */
|
|
6
|
+
lpActualBalances: bigint[];
|
|
7
|
+
decimals: number[];
|
|
8
|
+
bptTotalSupply: bigint;
|
|
9
|
+
swapFeeRate: number;
|
|
10
|
+
protocolFeeRate: number;
|
|
11
|
+
tokenInIndex: number;
|
|
12
|
+
amountIn: bigint;
|
|
13
|
+
/** Per-token input allocations from the quote (sum = amountIn). */
|
|
14
|
+
allocations: bigint[];
|
|
15
|
+
/** Per-leg expected swap outputs (0 for the input token / sidelined). */
|
|
16
|
+
expectedOuts: bigint[];
|
|
17
|
+
/** Amounts passed to add_liquidity after proportional capping. */
|
|
18
|
+
depositedAmounts: bigint[];
|
|
19
|
+
/** Helper-held excess refunded to the user. */
|
|
20
|
+
refundAmounts: bigint[];
|
|
21
|
+
estimatedBpt: bigint;
|
|
22
|
+
/**
|
|
23
|
+
* External per-token prices in any common unit. When omitted or incomplete
|
|
24
|
+
* the pool-spot-implied prices (w_i / V_i) are used instead.
|
|
25
|
+
*/
|
|
26
|
+
prices?: Array<number | null | undefined>;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Predicted total value loss of the LP position minted by a single-token
|
|
30
|
+
* deposit, as a percent of the deposited value, measured AFTER arbitrageurs
|
|
31
|
+
* rebalance the pool back to external prices — the slippage-proof cost the
|
|
32
|
+
* depositor actually bears.
|
|
33
|
+
*
|
|
34
|
+
* Replays the quote's swap legs and join onto the pool state, then values
|
|
35
|
+
* the position at the closed-form zero-fee-arb equilibrium: with the
|
|
36
|
+
* invariant ∏V_i^w_i preserved, equilibrium virtuals are V'_i = λ·w_i/p_i
|
|
37
|
+
* and actual balances move by the same deltas. Validated against a full
|
|
38
|
+
* profit-maximizing arbitrage simulation of the contract math (±0.03 pp,
|
|
39
|
+
* slightly conservative). Float math — ample for percent-level output.
|
|
40
|
+
*
|
|
41
|
+
* Returns `null` when the pool is empty or inputs cannot price.
|
|
42
|
+
*/
|
|
43
|
+
export declare function predictLpLoss(params: PredictLpLossParams): number | null;
|
|
44
|
+
//# sourceMappingURL=lpLoss.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"lpLoss.d.ts","sourceRoot":"","sources":["../../src/math/lpLoss.ts"],"names":[],"mappings":"AAMA,MAAM,WAAW,mBAAmB;IAClC,sDAAsD;IACtD,UAAU,EAAE,MAAM,EAAE,CAAC;IACrB,eAAe,EAAE,MAAM,EAAE,CAAC;IAC1B,yDAAyD;IACzD,gBAAgB,EAAE,MAAM,EAAE,CAAC;IAC3B,QAAQ,EAAE,MAAM,EAAE,CAAC;IACnB,cAAc,EAAE,MAAM,CAAC;IACvB,WAAW,EAAE,MAAM,CAAC;IACpB,eAAe,EAAE,MAAM,CAAC;IACxB,YAAY,EAAE,MAAM,CAAC;IACrB,QAAQ,EAAE,MAAM,CAAC;IACjB,mEAAmE;IACnE,WAAW,EAAE,MAAM,EAAE,CAAC;IACtB,yEAAyE;IACzE,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,kEAAkE;IAClE,gBAAgB,EAAE,MAAM,EAAE,CAAC;IAC3B,+CAA+C;IAC/C,aAAa,EAAE,MAAM,EAAE,CAAC;IACxB,YAAY,EAAE,MAAM,CAAC;IACrB;;;OAGG;IACH,MAAM,CAAC,EAAE,KAAK,CAAC,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC,CAAC;CAC3C;AAKD;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,aAAa,CAAC,MAAM,EAAE,mBAAmB,GAAG,MAAM,GAAG,IAAI,CA2GxE"}
|
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.predictLpLoss = predictLpLoss;
|
|
4
|
+
const config_1 = require("../config");
|
|
5
|
+
const toWhole = (raw, decimals) => Number(raw) / 10 ** decimals;
|
|
6
|
+
/**
|
|
7
|
+
* Predicted total value loss of the LP position minted by a single-token
|
|
8
|
+
* deposit, as a percent of the deposited value, measured AFTER arbitrageurs
|
|
9
|
+
* rebalance the pool back to external prices — the slippage-proof cost the
|
|
10
|
+
* depositor actually bears.
|
|
11
|
+
*
|
|
12
|
+
* Replays the quote's swap legs and join onto the pool state, then values
|
|
13
|
+
* the position at the closed-form zero-fee-arb equilibrium: with the
|
|
14
|
+
* invariant ∏V_i^w_i preserved, equilibrium virtuals are V'_i = λ·w_i/p_i
|
|
15
|
+
* and actual balances move by the same deltas. Validated against a full
|
|
16
|
+
* profit-maximizing arbitrage simulation of the contract math (±0.03 pp,
|
|
17
|
+
* slightly conservative). Float math — ample for percent-level output.
|
|
18
|
+
*
|
|
19
|
+
* Returns `null` when the pool is empty or inputs cannot price.
|
|
20
|
+
*/
|
|
21
|
+
function predictLpLoss(params) {
|
|
22
|
+
const { weightsBps, virtualBalances, lpActualBalances, decimals, bptTotalSupply, swapFeeRate, protocolFeeRate, tokenInIndex, amountIn, allocations, expectedOuts, depositedAmounts, refundAmounts, estimatedBpt, prices: externalPrices, } = params;
|
|
23
|
+
const n = weightsBps.length;
|
|
24
|
+
if (virtualBalances.length !== n ||
|
|
25
|
+
lpActualBalances.length !== n ||
|
|
26
|
+
decimals.length !== n) {
|
|
27
|
+
throw new Error("predictLpLoss: length mismatch");
|
|
28
|
+
}
|
|
29
|
+
if (tokenInIndex < 0 || tokenInIndex >= n) {
|
|
30
|
+
throw new Error("predictLpLoss: tokenInIndex out of range");
|
|
31
|
+
}
|
|
32
|
+
const supply = Number(bptTotalSupply);
|
|
33
|
+
const estBpt = Number(estimatedBpt);
|
|
34
|
+
const amountInWhole = toWhole(amountIn, decimals[tokenInIndex]);
|
|
35
|
+
if (supply <= 0 || estBpt <= 0 || amountInWhole <= 0)
|
|
36
|
+
return null;
|
|
37
|
+
const weights = [];
|
|
38
|
+
const virtuals = [];
|
|
39
|
+
const actuals = [];
|
|
40
|
+
for (let i = 0; i < n; i++) {
|
|
41
|
+
weights.push(weightsBps[i] / config_1.WEIGHT_SCALE);
|
|
42
|
+
virtuals.push(toWhole(virtualBalances[i], decimals[i]));
|
|
43
|
+
actuals.push(toWhole(lpActualBalances[i], decimals[i]));
|
|
44
|
+
}
|
|
45
|
+
const externalComplete = externalPrices !== undefined &&
|
|
46
|
+
externalPrices.length === n &&
|
|
47
|
+
externalPrices.every((p) => typeof p === "number" && p > 0);
|
|
48
|
+
const prices = [];
|
|
49
|
+
for (let i = 0; i < n; i++) {
|
|
50
|
+
const price = externalComplete
|
|
51
|
+
? externalPrices[i]
|
|
52
|
+
: weights[i] / virtuals[i];
|
|
53
|
+
if (!Number.isFinite(price) || price <= 0)
|
|
54
|
+
return null;
|
|
55
|
+
prices.push(price);
|
|
56
|
+
}
|
|
57
|
+
const feeRate = swapFeeRate / config_1.SWAP_FEE_PRECISION;
|
|
58
|
+
const protoRate = protocolFeeRate / config_1.PROTOCOL_FEE_PRECISION;
|
|
59
|
+
for (let i = 0; i < n; i++) {
|
|
60
|
+
if (i === tokenInIndex)
|
|
61
|
+
continue;
|
|
62
|
+
const alloc = toWhole(allocations[i] ?? 0n, decimals[tokenInIndex]);
|
|
63
|
+
const out = toWhole(expectedOuts[i] ?? 0n, decimals[i]);
|
|
64
|
+
if (alloc <= 0 || out <= 0)
|
|
65
|
+
continue;
|
|
66
|
+
const protoFee = alloc * feeRate * protoRate;
|
|
67
|
+
virtuals[tokenInIndex] += alloc - protoFee;
|
|
68
|
+
actuals[tokenInIndex] += alloc - protoFee;
|
|
69
|
+
virtuals[i] -= out;
|
|
70
|
+
actuals[i] -= out;
|
|
71
|
+
}
|
|
72
|
+
const mintRatio = estBpt / supply;
|
|
73
|
+
for (let i = 0; i < n; i++) {
|
|
74
|
+
actuals[i] += toWhole(depositedAmounts[i] ?? 0n, decimals[i]);
|
|
75
|
+
virtuals[i] *= 1 + mintRatio;
|
|
76
|
+
}
|
|
77
|
+
let logInvariant = 0;
|
|
78
|
+
let logTarget = 0;
|
|
79
|
+
for (let i = 0; i < n; i++) {
|
|
80
|
+
if (weights[i] <= 0 || virtuals[i] <= 0)
|
|
81
|
+
return null;
|
|
82
|
+
logInvariant += weights[i] * Math.log(virtuals[i]);
|
|
83
|
+
logTarget += weights[i] * Math.log(weights[i] / prices[i]);
|
|
84
|
+
}
|
|
85
|
+
const lambda = Math.exp(logInvariant - logTarget);
|
|
86
|
+
let equilibriumPoolValue = 0;
|
|
87
|
+
for (let i = 0; i < n; i++) {
|
|
88
|
+
const equilibriumVirtual = (lambda * weights[i]) / prices[i];
|
|
89
|
+
const equilibriumActual = Math.max(0, actuals[i] - (virtuals[i] - equilibriumVirtual));
|
|
90
|
+
equilibriumPoolValue += equilibriumActual * prices[i];
|
|
91
|
+
}
|
|
92
|
+
const lpValue = (mintRatio / (1 + mintRatio)) * equilibriumPoolValue;
|
|
93
|
+
let refundValue = 0;
|
|
94
|
+
for (let i = 0; i < n; i++) {
|
|
95
|
+
refundValue += toWhole(refundAmounts[i] ?? 0n, decimals[i]) * prices[i];
|
|
96
|
+
}
|
|
97
|
+
const depositValue = amountInWhole * prices[tokenInIndex];
|
|
98
|
+
if (depositValue <= 0)
|
|
99
|
+
return null;
|
|
100
|
+
const loss = 1 - (lpValue + refundValue) / depositValue;
|
|
101
|
+
return Math.min(100, Math.max(0, loss * 100));
|
|
102
|
+
}
|
|
103
|
+
//# sourceMappingURL=lpLoss.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"lpLoss.js","sourceRoot":"","sources":["../../src/math/lpLoss.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,164 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Sliding-window cumulative-sell rate limiter + variable sell-off surge fee.
|
|
3
|
+
*
|
|
4
|
+
* Port of the v5.1 (post-audit) contracts:
|
|
5
|
+
* `programs/cubic-pool/src/math/max_selloff.rs` (`check_and_advance`)
|
|
6
|
+
* `programs/cubic-pool/src/math/surge_fee.rs` (`calc_surge_fee_pct`)
|
|
7
|
+
* `programs/cubic-pool/src/instructions/user/swap.rs` (segmented charge)
|
|
8
|
+
*
|
|
9
|
+
* All arithmetic is bigint, mirroring the Rust u128 intermediates INCLUDING
|
|
10
|
+
* integer-division order — do not "simplify" a `a*b/c` into a different
|
|
11
|
+
* association, parity with the on-chain result depends on it. BN appears
|
|
12
|
+
* only at the SDK boundary.
|
|
13
|
+
*
|
|
14
|
+
* v5.1 curve model: the fee RATE is piecewise-LINEAR in the normalized
|
|
15
|
+
* window-fill coordinate `t ∈ [0, 1]` (threshold → 100% fill):
|
|
16
|
+
* - no kink: low → high over [0, 1]
|
|
17
|
+
* - kinked: low → mid over [0, k], mid → high over [k, 1]
|
|
18
|
+
* and a swap is charged the AVERAGE rate over the span it crosses
|
|
19
|
+
* (integral / width), which makes the fee path-independent — splitting a
|
|
20
|
+
* sell into parts cannot cheapen it (audit M-05). The old exponential
|
|
21
|
+
* convexity curve (A^t) is gone.
|
|
22
|
+
*/
|
|
23
|
+
import BN from "bn.js";
|
|
24
|
+
/** Mirrors cubic-pool::constants::SURGE_FEE_SEGMENTS. */
|
|
25
|
+
export declare const SURGE_FEE_SEGMENTS = 4;
|
|
26
|
+
export interface SelloffWindowInputs {
|
|
27
|
+
maxSelloffPct: number;
|
|
28
|
+
periodLength: number;
|
|
29
|
+
previousSelloff: BN;
|
|
30
|
+
currentSelloff: BN;
|
|
31
|
+
windowStartTimestamp: BN;
|
|
32
|
+
selloffVbSnapshot: BN;
|
|
33
|
+
/** Current pre-trade virtual balance of the token. */
|
|
34
|
+
virtualBalance: BN;
|
|
35
|
+
/** Unix seconds. */
|
|
36
|
+
now: number;
|
|
37
|
+
}
|
|
38
|
+
export interface SelloffWindowStatus {
|
|
39
|
+
/** True when the limiter is configured (`maxSelloffPct > 0`). */
|
|
40
|
+
enabled: boolean;
|
|
41
|
+
cap: BN;
|
|
42
|
+
/** Effective decayed usage WITHOUT a hypothetical trade. */
|
|
43
|
+
used: BN;
|
|
44
|
+
/** `max(0, cap - used)`. */
|
|
45
|
+
remaining: BN;
|
|
46
|
+
/** `used/cap` in PERCENT_SCALE units (0..10_000+); 0 when disabled/cap=0. */
|
|
47
|
+
fillPct: number;
|
|
48
|
+
windowStartTimestamp: BN;
|
|
49
|
+
periodLength: number;
|
|
50
|
+
/** Whether the projection at `now` rotated the window vs stored state. */
|
|
51
|
+
rotated: boolean;
|
|
52
|
+
/** Snapshot the cap was resolved against (post-projection). */
|
|
53
|
+
vbSnapshot: BN;
|
|
54
|
+
}
|
|
55
|
+
/** Result of the pure bigint window projection. */
|
|
56
|
+
export interface WindowProjection {
|
|
57
|
+
opened: boolean;
|
|
58
|
+
windowStart: bigint;
|
|
59
|
+
elapsedInWindow: bigint;
|
|
60
|
+
/** Carried-over previous usage, POST v5.1 snapshot rescale. */
|
|
61
|
+
previous: bigint;
|
|
62
|
+
current: bigint;
|
|
63
|
+
vbSnapshot: bigint;
|
|
64
|
+
cap: bigint;
|
|
65
|
+
weightedPrev: bigint;
|
|
66
|
+
/** weightedPrev + current (decayed effective, WITHOUT a hypothetical trade). */
|
|
67
|
+
usedWithoutTrade: bigint;
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Pure bigint projection of the sliding window at `now`. Mirrors v5.1
|
|
71
|
+
* `check_and_advance`'s rotation + snapshot logic (read-only, no
|
|
72
|
+
* `amount_in`), including the audit addition: when the projection OPENS a
|
|
73
|
+
* window against a new vb snapshot, the carried-over `previous` usage is
|
|
74
|
+
* rescaled by `newSnapshot / oldSnapshot` so a liquidity change between
|
|
75
|
+
* windows doesn't distort the carried percentage.
|
|
76
|
+
*/
|
|
77
|
+
export declare function projectSelloffWindow(params: {
|
|
78
|
+
maxSelloffPct: number;
|
|
79
|
+
periodLength: number;
|
|
80
|
+
previousSelloff: bigint;
|
|
81
|
+
currentSelloff: bigint;
|
|
82
|
+
windowStartTimestamp: bigint;
|
|
83
|
+
selloffVbSnapshot: bigint;
|
|
84
|
+
virtualBalance: bigint;
|
|
85
|
+
now: number;
|
|
86
|
+
}): WindowProjection;
|
|
87
|
+
/** Read-only status of a token's max-selloff window at `now`. */
|
|
88
|
+
export declare function computeSelloffWindow(inputs: SelloffWindowInputs): SelloffWindowStatus;
|
|
89
|
+
/**
|
|
90
|
+
* Average surge-fee percentage (PERCENT_SCALE units, 0..=10_000) charged for
|
|
91
|
+
* moving the window fill from `effectiveSelloffBefore` to
|
|
92
|
+
* `effectiveSelloffAfter` against `cap`. Port of v5.1 `calc_surge_fee_pct`:
|
|
93
|
+
* the rate is INTEGRATED over the crossed span (CEIL), so the charge is
|
|
94
|
+
* path-independent. When the span is empty (`after <= before`) the point
|
|
95
|
+
* rate at `after` is returned.
|
|
96
|
+
*/
|
|
97
|
+
export declare function calcSurgeFeePct(effectiveSelloffBefore: bigint, effectiveSelloffAfter: bigint, cap: bigint, thresholdPct: number, slopeLowPct: number, slopeMidPct: number, slopeHighPct: number, kinkPct: number): number;
|
|
98
|
+
/**
|
|
99
|
+
* CEIL fee application of a known percentage on `amount`, clamped to
|
|
100
|
+
* `amount`. NOTE: the contract does NOT charge the whole output at one
|
|
101
|
+
* rate — use {@link calcSegmentedSurgeFeeAmount} to mirror an actual swap.
|
|
102
|
+
* This helper remains for coarse display math only.
|
|
103
|
+
*/
|
|
104
|
+
export declare function calcSurgeFeeAmount(amountOut: bigint, surgePct: number): bigint;
|
|
105
|
+
export interface SegmentedSurgeFeeParams {
|
|
106
|
+
/** Window fill before the trade (`usedWithoutTrade`). */
|
|
107
|
+
effectiveSelloffBefore: bigint;
|
|
108
|
+
/** Window fill after the trade (`before + amountInNet`). */
|
|
109
|
+
effectiveSelloffAfter: bigint;
|
|
110
|
+
cap: bigint;
|
|
111
|
+
thresholdPct: number;
|
|
112
|
+
slopeLowPct: number;
|
|
113
|
+
slopeMidPct: number;
|
|
114
|
+
slopeHighPct: number;
|
|
115
|
+
kinkPct: number;
|
|
116
|
+
/** Post-swap-fee input driving the AMM curve (`amount_in_after_fee`). */
|
|
117
|
+
amountInAfterFee: bigint;
|
|
118
|
+
/** Full curve output of the trade (gross, pre-surge). */
|
|
119
|
+
amountOut: bigint;
|
|
120
|
+
/**
|
|
121
|
+
* Cumulative AMM output for an input slice `x ∈ [0, amountInAfterFee]`
|
|
122
|
+
* against the PRE-TRADE balances (i.e. `calc_out_given_in` with the same
|
|
123
|
+
* arguments that produced `amountOut`).
|
|
124
|
+
*/
|
|
125
|
+
curveOut: (amountInSlice: bigint) => bigint;
|
|
126
|
+
/** Defaults to the contract's SURGE_FEE_SEGMENTS (= 4). */
|
|
127
|
+
segments?: number;
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* Surge fee in OUTPUT-token units for one swap — the exact v5.1 on-chain
|
|
131
|
+
* charge (swap.rs): only the output produced ABOVE the threshold is taxed,
|
|
132
|
+
* segment by segment across the taxed span, each segment's REAL curve
|
|
133
|
+
* output at that segment's average rate (CEIL per segment), total clamped
|
|
134
|
+
* to `amountOut`. Charging one average rate on the whole output would
|
|
135
|
+
* re-open the audit M-05 split dodge on asymmetric pools.
|
|
136
|
+
*/
|
|
137
|
+
export declare function calcSegmentedSurgeFeeAmount(p: SegmentedSurgeFeeParams): bigint;
|
|
138
|
+
export interface SelloffState {
|
|
139
|
+
previousSelloff: bigint;
|
|
140
|
+
currentSelloff: bigint;
|
|
141
|
+
windowStartTimestamp: bigint;
|
|
142
|
+
selloffVbSnapshot: bigint;
|
|
143
|
+
}
|
|
144
|
+
export interface SelloffResult {
|
|
145
|
+
effectiveSelloffBefore: bigint;
|
|
146
|
+
effectiveSelloff: bigint;
|
|
147
|
+
maxSelloffCap: bigint;
|
|
148
|
+
vbSnapshot: bigint;
|
|
149
|
+
previousSelloff: bigint;
|
|
150
|
+
currentSelloff: bigint;
|
|
151
|
+
windowStartTimestamp: bigint;
|
|
152
|
+
}
|
|
153
|
+
/** Pure: does not modify its input, including on rejection. */
|
|
154
|
+
export declare function checkAndAdvanceSelloff(params: {
|
|
155
|
+
state: SelloffState;
|
|
156
|
+
maxSelloffPct: number;
|
|
157
|
+
period: number;
|
|
158
|
+
amountIn: bigint;
|
|
159
|
+
virtualBalance: bigint;
|
|
160
|
+
now: bigint;
|
|
161
|
+
}): SelloffResult | null;
|
|
162
|
+
/** Mirror of window rescaling after proportional add/remove liquidity. */
|
|
163
|
+
export declare function rescaleSelloffWindow(state: SelloffState, ratio: bigint, isIncrease: boolean, maxSelloffPct: number): SelloffState;
|
|
164
|
+
//# sourceMappingURL=maxSelloff.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"maxSelloff.d.ts","sourceRoot":"","sources":["../../src/math/maxSelloff.ts"],"names":[],"mappings":"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"}
|