@gearbox-protocol/sdk 16.4.0-next.2 → 16.4.0-next.3

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.
@@ -183,7 +183,10 @@ var CreditAccountOperationsService = class extends require_onchain_base_SDKConst
183
183
  });
184
184
  return {
185
185
  ...result,
186
- state: tail.state,
186
+ state: {
187
+ ...tail.state,
188
+ executionCost: result.state.executionCost
189
+ },
187
190
  delayed
188
191
  };
189
192
  } catch (e) {
@@ -1,4 +1,5 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
+ const require_onchain_constants_math = require("../../constants/math.js");
2
3
  const require_model_errors_operation_errors = require("../../../model/errors/operation-errors.js");
3
4
  const require_model_errors_prepare_errors = require("../../../model/errors/prepare-errors.js");
4
5
  require("../../../model/index.js");
@@ -73,6 +74,26 @@ async function realize(steps, props) {
73
74
  let raised = 0n;
74
75
  /** The request, before the walk's end state can be attached to it. */
75
76
  let delayed;
77
+ /** Oracle value in the underlying of what routed legs and requests spend and return. */
78
+ const traded = {
79
+ spentUnd: 0n,
80
+ returnedUnd: 0n,
81
+ priced: true
82
+ };
83
+ const trade = (spent, returned) => {
84
+ const underlyingValue = (legs) => {
85
+ let sum = 0n;
86
+ for (const { token, amount } of legs) {
87
+ if (amount === 0n) continue;
88
+ const value = price(token, underlying, amount);
89
+ if (value <= 0n) traded.priced = false;
90
+ sum += value;
91
+ }
92
+ return sum;
93
+ };
94
+ traded.spentUnd += underlyingValue(spent);
95
+ traded.returnedUnd += underlyingValue(returned);
96
+ };
76
97
  /**
77
98
  * Set by a `clearQuotas` step, which settles the quotas mid-walk instead of
78
99
  * at the end — and settles them at none, whatever the balances turn out to be.
@@ -174,6 +195,13 @@ async function realize(steps, props) {
174
195
  ...swap,
175
196
  amountOut: leg.amount
176
197
  });
198
+ trade([{
199
+ token: step.from,
200
+ amount
201
+ }], [{
202
+ token: step.to,
203
+ amount: leg.amount
204
+ }]);
177
205
  raised = leg.minAmount;
178
206
  break;
179
207
  }
@@ -199,6 +227,13 @@ async function realize(steps, props) {
199
227
  })),
200
228
  amountOut: leg.amount
201
229
  });
230
+ trade(balances.map((a) => ({
231
+ token: a.token,
232
+ amount: a.balance
233
+ })), [{
234
+ token: underlying,
235
+ amount: leg.amount
236
+ }]);
202
237
  }
203
238
  }
204
239
  raised = ledger.balanceOf(underlying);
@@ -243,6 +278,13 @@ async function realize(steps, props) {
243
278
  amount: require_onchain_accounts_intents_utils_common.toTargetDecimals(queued.amount, queued.token, asset.underlying, sdk)
244
279
  } : void 0
245
280
  };
281
+ trade([{
282
+ token: preview.token,
283
+ amount: preview.amountIn
284
+ }], [...preview.outputs.filter((o) => !o.isDelayed).map((o) => ({
285
+ token: o.token,
286
+ amount: o.amount
287
+ })), ...delayed.claim ? [delayed.claim] : []]);
246
288
  raised = require_onchain_accounts_intents_operations.instantOutput(preview.outputs)?.amount ?? 0n;
247
289
  break;
248
290
  }
@@ -338,9 +380,11 @@ async function realize(steps, props) {
338
380
  netValue: projected.totalValue - debt,
339
381
  toUnderlying: (from, amount) => price(from, underlying, amount)
340
382
  });
383
+ const executionCost = traded.priced && traded.spentUnd > 0n ? require_onchain_constants_math.PERCENTAGE_FACTOR_1KK * (traded.returnedUnd - traded.spentUnd) / traded.spentUnd : void 0;
341
384
  const state = {
342
385
  ...projection,
343
386
  priceImpact,
387
+ executionCost,
344
388
  currentPrice: sdk.positions.currentPrice(snapshot)
345
389
  };
346
390
  return {
@@ -19,12 +19,12 @@ function probeBasket(balances, oracle) {
19
19
  if (usd > 0n) basketWad += usd * require_onchain_constants_math.WAD / require_onchain_constants_math.PRICE_DECIMALS;
20
20
  }
21
21
  if (basketWad <= 0n) return;
22
- const probeWad = PROBE_UNIT_USD_WAD;
23
22
  const scaled = balances.map((asset) => ({
24
23
  token: asset.token,
25
- balance: asset.balance * probeWad / basketWad
24
+ balance: asset.balance * PROBE_UNIT_USD_WAD / basketWad
26
25
  }));
27
- if (!scaled.some((a) => a.balance > 0n)) return;
26
+ const probeWad = scaled.reduce((sum, a) => sum + oracle.safeConvertToUSD(a.token, a.balance).value * require_onchain_constants_math.WAD / require_onchain_constants_math.PRICE_DECIMALS, 0n);
27
+ if (probeWad <= 0n) return;
28
28
  return {
29
29
  balances: scaled,
30
30
  basketWad,
@@ -182,7 +182,10 @@ var CreditAccountOperationsService = class extends SDKConstruct {
182
182
  });
183
183
  return {
184
184
  ...result,
185
- state: tail.state,
185
+ state: {
186
+ ...tail.state,
187
+ executionCost: result.state.executionCost
188
+ },
186
189
  delayed
187
190
  };
188
191
  } catch (e) {
@@ -1,3 +1,4 @@
1
+ import { PERCENTAGE_FACTOR_1KK } from "../../constants/math.js";
1
2
  import { insufficientBalance } from "../../../model/errors/operation-errors.js";
2
3
  import { multipleDelayedWithdrawals, noDelayedRoute, withdrawalInProgress } from "../../../model/errors/prepare-errors.js";
3
4
  import "../../../model/index.js";
@@ -72,6 +73,26 @@ async function realize(steps, props) {
72
73
  let raised = 0n;
73
74
  /** The request, before the walk's end state can be attached to it. */
74
75
  let delayed;
76
+ /** Oracle value in the underlying of what routed legs and requests spend and return. */
77
+ const traded = {
78
+ spentUnd: 0n,
79
+ returnedUnd: 0n,
80
+ priced: true
81
+ };
82
+ const trade = (spent, returned) => {
83
+ const underlyingValue = (legs) => {
84
+ let sum = 0n;
85
+ for (const { token, amount } of legs) {
86
+ if (amount === 0n) continue;
87
+ const value = price(token, underlying, amount);
88
+ if (value <= 0n) traded.priced = false;
89
+ sum += value;
90
+ }
91
+ return sum;
92
+ };
93
+ traded.spentUnd += underlyingValue(spent);
94
+ traded.returnedUnd += underlyingValue(returned);
95
+ };
75
96
  /**
76
97
  * Set by a `clearQuotas` step, which settles the quotas mid-walk instead of
77
98
  * at the end — and settles them at none, whatever the balances turn out to be.
@@ -173,6 +194,13 @@ async function realize(steps, props) {
173
194
  ...swap,
174
195
  amountOut: leg.amount
175
196
  });
197
+ trade([{
198
+ token: step.from,
199
+ amount
200
+ }], [{
201
+ token: step.to,
202
+ amount: leg.amount
203
+ }]);
176
204
  raised = leg.minAmount;
177
205
  break;
178
206
  }
@@ -198,6 +226,13 @@ async function realize(steps, props) {
198
226
  })),
199
227
  amountOut: leg.amount
200
228
  });
229
+ trade(balances.map((a) => ({
230
+ token: a.token,
231
+ amount: a.balance
232
+ })), [{
233
+ token: underlying,
234
+ amount: leg.amount
235
+ }]);
201
236
  }
202
237
  }
203
238
  raised = ledger.balanceOf(underlying);
@@ -242,6 +277,13 @@ async function realize(steps, props) {
242
277
  amount: toTargetDecimals(queued.amount, queued.token, asset.underlying, sdk)
243
278
  } : void 0
244
279
  };
280
+ trade([{
281
+ token: preview.token,
282
+ amount: preview.amountIn
283
+ }], [...preview.outputs.filter((o) => !o.isDelayed).map((o) => ({
284
+ token: o.token,
285
+ amount: o.amount
286
+ })), ...delayed.claim ? [delayed.claim] : []]);
245
287
  raised = instantOutput(preview.outputs)?.amount ?? 0n;
246
288
  break;
247
289
  }
@@ -337,9 +379,11 @@ async function realize(steps, props) {
337
379
  netValue: projected.totalValue - debt,
338
380
  toUnderlying: (from, amount) => price(from, underlying, amount)
339
381
  });
382
+ const executionCost = traded.priced && traded.spentUnd > 0n ? PERCENTAGE_FACTOR_1KK * (traded.returnedUnd - traded.spentUnd) / traded.spentUnd : void 0;
340
383
  const state = {
341
384
  ...projection,
342
385
  priceImpact,
386
+ executionCost,
343
387
  currentPrice: sdk.positions.currentPrice(snapshot)
344
388
  };
345
389
  return {
@@ -18,12 +18,12 @@ function probeBasket(balances, oracle) {
18
18
  if (usd > 0n) basketWad += usd * WAD / PRICE_DECIMALS;
19
19
  }
20
20
  if (basketWad <= 0n) return;
21
- const probeWad = PROBE_UNIT_USD_WAD;
22
21
  const scaled = balances.map((asset) => ({
23
22
  token: asset.token,
24
- balance: asset.balance * probeWad / basketWad
23
+ balance: asset.balance * PROBE_UNIT_USD_WAD / basketWad
25
24
  }));
26
- if (!scaled.some((a) => a.balance > 0n)) return;
25
+ const probeWad = scaled.reduce((sum, a) => sum + oracle.safeConvertToUSD(a.token, a.balance).value * WAD / PRICE_DECIMALS, 0n);
26
+ if (probeWad <= 0n) return;
27
27
  return {
28
28
  balances: scaled,
29
29
  basketWad,
@@ -62,7 +62,16 @@ interface SimulationPrices {
62
62
  * {@link AccountProjection} vocabulary, plus the prices only a routed walk can
63
63
  * report.
64
64
  */
65
- interface OperationState extends AccountProjection, SimulationPrices {}
65
+ interface OperationState extends AccountProjection, SimulationPrices {
66
+ /**
67
+ * What the operation gives up, as `(out − in) / in`: the oracle value in the
68
+ * underlying of everything its routed legs and redemption request return,
69
+ * the expected claim included, against the value of what they spend.
70
+ * In `PERCENTAGE_FACTOR_1KK` (1_000_000 = 100%), negative for a loss.
71
+ * `undefined` where nothing was traded or a leg cannot be priced.
72
+ */
73
+ executionCost: bigint | undefined;
74
+ }
66
75
  /**
67
76
  * What planning an intent yields: the operation chain, the state it projects,
68
77
  * and the calldata that realises it — or the error that stopped the plan.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@gearbox-protocol/sdk",
3
- "version": "16.4.0-next.2",
3
+ "version": "16.4.0-next.3",
4
4
  "description": "Gearbox SDK",
5
5
  "license": "MIT",
6
6
  "repository": {