@ckb-ccc/core 1.22.0 → 1.22.1

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ckb-ccc/core",
3
- "version": "1.22.0",
3
+ "version": "1.22.1",
4
4
  "description": "Core of CCC - CKBer's Codebase",
5
5
  "author": "Hanssen0 <hanssen0@hanssen0.com>",
6
6
  "license": "MIT",
@@ -2497,13 +2497,22 @@ export class Transaction extends Entity.Base<TransactionLike, Transaction>() {
2497
2497
  const needed = numFrom(
2498
2498
  await Promise.resolve(change(changedTx, fee - leastFee)),
2499
2499
  );
2500
+
2500
2501
  if (needed > Zero) {
2501
2502
  // No enough extra capacity to create new cells for change, collect inputs again
2502
2503
  leastExtraCapacity = needed;
2503
2504
  continue;
2504
2505
  }
2505
2506
 
2506
- if ((await changedTx.getFee(from.client)) !== leastFee) {
2507
+ const changedActualFee = await changedTx.getFee(from.client);
2508
+ if (changedActualFee < leastFee && fee < leastFee) {
2509
+ // Fee is not fully paid yet because the initial transaction had insufficient inputs.
2510
+ // Collect inputs again to pay leastFee.
2511
+ leastExtraCapacity = Zero;
2512
+ continue;
2513
+ }
2514
+
2515
+ if (changedActualFee !== leastFee) {
2507
2516
  throw new Error(
2508
2517
  "The change function doesn't use all available capacity",
2509
2518
  );
@@ -2671,14 +2680,21 @@ export class Transaction extends Entity.Base<TransactionLike, Transaction>() {
2671
2680
  shouldAddInputs?: boolean;
2672
2681
  },
2673
2682
  ): Promise<[number, boolean]> {
2674
- const change = Number(numFrom(index));
2675
- if (!this.outputs[change]) {
2683
+ const change = transactionIndexFrom(index);
2684
+ if (change === undefined || !this.outputs[change]) {
2676
2685
  throw new Error("Non-existed output to change");
2677
2686
  }
2678
2687
  return this.completeFee(
2679
2688
  from,
2680
2689
  (tx, capacity) => {
2681
- tx.outputs[change].capacity += capacity;
2690
+ tx.setOutput(
2691
+ change,
2692
+ {
2693
+ ...tx.outputs[change],
2694
+ capacity: tx.outputs[change].capacity + capacity,
2695
+ },
2696
+ tx.outputsData[change],
2697
+ );
2682
2698
  return 0;
2683
2699
  },
2684
2700
  feeRate,
@@ -178,7 +178,7 @@ export abstract class ClientJsonRpc extends Client {
178
178
 
179
179
  getFeeRateStatistics = this.buildSender(
180
180
  "get_fee_rate_statistics",
181
- [(n: NumLike) => apply(numFrom, n)],
181
+ [(n?: NumLike) => apply(numToHex, n)],
182
182
  // TODO: This is a temporary workaround for the fact that the node may return null for fee rate statistics.
183
183
  // We should change the method signature to return null instead of falling back to the default value,
184
184
  // but this would be a breaking change.
@@ -30,7 +30,11 @@ export type FixedPointLike = bigint | string | number;
30
30
  */
31
31
 
32
32
  export function fixedPointToString(val: FixedPointLike, decimals = 8): string {
33
- const str = fixedPointFrom(val).toString();
33
+ const fp = fixedPointFrom(val, decimals);
34
+ if (fp < 0n) {
35
+ return `-${fixedPointToString(-fp, decimals)}`;
36
+ }
37
+ const str = fp.toString();
34
38
  if (decimals === 0) {
35
39
  return str;
36
40
  }
@@ -65,15 +69,20 @@ export function fixedPointFrom(val: FixedPointLike, decimals = 8): FixedPoint {
65
69
  return val;
66
70
  }
67
71
 
68
- const [l, r] = (
69
- typeof val === "number" ? val.toFixed(decimals) : val.toString()
70
- ).split(".");
71
- const lVal = BigInt(l.padEnd(l.length + decimals, "0"));
72
- if (r === undefined) {
73
- return lVal;
72
+ let str = typeof val === "number" ? val.toFixed(decimals) : val.toString();
73
+ const isNegative = str.startsWith("-");
74
+ if (isNegative || str.startsWith("+")) {
75
+ str = str.slice(1);
76
+ }
77
+
78
+ const [l, r] = str.split(".");
79
+ const lVal = l === "" ? 0n : BigInt(l.padEnd(l.length + decimals, "0"));
80
+ if (r === undefined || decimals === 0) {
81
+ return isNegative ? -lVal : lVal;
74
82
  }
75
83
 
76
- return lVal + BigInt(r.slice(0, decimals).padEnd(decimals, "0"));
84
+ const unsignedVal = lVal + BigInt(r.slice(0, decimals).padEnd(decimals, "0"));
85
+ return isNegative ? -unsignedVal : unsignedVal;
77
86
  }
78
87
 
79
88
  /**
@@ -209,7 +209,9 @@ export class JsonRpcTransportWebSocket implements JsonRpcTransport {
209
209
  this.disposed = true;
210
210
  const socket = this.socket;
211
211
 
212
- if (!socket || socket.readyState === socket.CLOSED) return;
212
+ if (!socket || socket.readyState === socket.CLOSED) {
213
+ return;
214
+ }
213
215
 
214
216
  await new Promise<void>((resolve) => {
215
217
  socket.addEventListener("close", () => resolve(), { once: true });
@@ -326,7 +326,9 @@ export async function waitForAvailability(signal?: AbortSignal): Promise<void> {
326
326
  }
327
327
 
328
328
  function onAbort() {
329
- if (settled) return;
329
+ if (settled) {
330
+ return;
331
+ }
330
332
 
331
333
  settled = true;
332
334
  cleanup();