From 0d654117189321e0bce82b7c38dc8f05ac4aec95 Mon Sep 17 00:00:00 2001 From: fgh Date: Tue, 30 Dec 2025 15:04:24 -0500 Subject: [PATCH 1/3] feat(core): add RGB++ script support to known scripts --- .../client/clientPublicMainnet.advanced.ts | 68 +++++++++++++++++++ .../client/clientPublicTestnet.advanced.ts | 68 +++++++++++++++++++ packages/core/src/client/knownScript.ts | 4 ++ 3 files changed, 140 insertions(+) diff --git a/packages/core/src/client/clientPublicMainnet.advanced.ts b/packages/core/src/client/clientPublicMainnet.advanced.ts index 979b0955c..90c1b9c52 100644 --- a/packages/core/src/client/clientPublicMainnet.advanced.ts +++ b/packages/core/src/client/clientPublicMainnet.advanced.ts @@ -457,4 +457,72 @@ export const MAINNET_SCRIPTS: Record = }, ], }, + [KnownScript.RgbppLock]: { + codeHash: + "0xbc6c568a1a0d0a09f6844dc9d74ddb4343c32143ff25f727c59edf4fb72d6936", + hashType: "type", + cellDeps: [ + { + cellDep: { + outPoint: { + txHash: + "0xcb4d9f9726e66306bfda6359d39d3bea8b4e5345d0f95f26a3e51626ebe82a63", + index: 0, + }, + depType: "code", + }, + type: { + codeHash: + "0x00000000000000000000000000000000000000000000000000545950455f4944", + hashType: "type", + args: "0x68ad3d9e0bb9ea841a5d1fcd600137bd3f45401e759e353121f26cd0d981452f", + }, + }, + // Rgbpp lock config cell dep + { + cellDep: { + outPoint: { + txHash: + "0xcb4d9f9726e66306bfda6359d39d3bea8b4e5345d0f95f26a3e51626ebe82a63", + index: 1, + }, + depType: "code", + }, + }, + ], + }, + [KnownScript.BtcTimeLock]: { + codeHash: + "0x70d64497a075bd651e98ac030455ea200637ee325a12ad08aff03f1a117e5a62", + hashType: "type", + cellDeps: [ + { + cellDep: { + outPoint: { + txHash: + "0x3d1c26b966504b09253ad84173bf3baa7b8135c5ff520c32cf70b631c1d08b9b", + index: 0, + }, + depType: "code", + }, + type: { + codeHash: + "0x00000000000000000000000000000000000000000000000000545950455f4944", + hashType: "type", + args: "0x44b8253ae18e913a2845b0d548eaf6b3ba1099ed26835888932a754194028a8a", + }, + }, + // btc time lock config cell dep + { + cellDep: { + outPoint: { + txHash: + "0x3d1c26b966504b09253ad84173bf3baa7b8135c5ff520c32cf70b631c1d08b9b", + index: 1, + }, + depType: "code", + }, + }, + ], + }, }); diff --git a/packages/core/src/client/clientPublicTestnet.advanced.ts b/packages/core/src/client/clientPublicTestnet.advanced.ts index be811c7eb..c38074b0b 100644 --- a/packages/core/src/client/clientPublicTestnet.advanced.ts +++ b/packages/core/src/client/clientPublicTestnet.advanced.ts @@ -469,4 +469,72 @@ export const TESTNET_SCRIPTS: Record = }, ], }, + [KnownScript.RgbppLock]: { + codeHash: + "0x61ca7a4796a4eb19ca4f0d065cb9b10ddcf002f10f7cbb810c706cb6bb5c3248", + hashType: "type", + cellDeps: [ + { + cellDep: { + outPoint: { + txHash: + "0x0d1567da0979f78b297d5311442669fbd1bd853c8be324c5ab6da41e7a1ed6e5", + index: 0, + }, + depType: "code", + }, + type: { + codeHash: + "0x00000000000000000000000000000000000000000000000000545950455f4944", + hashType: "type", + args: "0xa3bc8441df149def76cfe15fec7b1e51d949548bc27fb7a75e9d4b3ef1c12c7f", + }, + }, + // Rgbpp lock config cell dep for Bitcoin Testnet3 + { + cellDep: { + outPoint: { + txHash: + "0x0d1567da0979f78b297d5311442669fbd1bd853c8be324c5ab6da41e7a1ed6e5", + index: 1, + }, + depType: "code", + }, + }, + ], + }, + [KnownScript.BtcTimeLock]: { + codeHash: + "0x00cdf8fab0f8ac638758ebf5ea5e4052b1d71e8a77b9f43139718621f6849326", + hashType: "type", + cellDeps: [ + { + cellDep: { + outPoint: { + txHash: + "0x8fb747ff0416a43e135c583b028f98c7b81d3770551b196eb7ba1062dd9acc94", + index: 0, + }, + depType: "code", + }, + type: { + codeHash: + "0x00000000000000000000000000000000000000000000000000545950455f4944", + hashType: "type", + args: "0xc9828585e6dd2afacb9e6e8ca7deb0975121aabee5c7983178a45509ffaec984", + }, + }, + // btc time lock config cell dep for Bitcoin Testnet3 + { + cellDep: { + outPoint: { + txHash: + "0x8fb747ff0416a43e135c583b028f98c7b81d3770551b196eb7ba1062dd9acc94", + index: 1, + }, + depType: "code", + }, + }, + ], + }, }); diff --git a/packages/core/src/client/knownScript.ts b/packages/core/src/client/knownScript.ts index 2171b90b4..c65259c61 100644 --- a/packages/core/src/client/knownScript.ts +++ b/packages/core/src/client/knownScript.ts @@ -25,4 +25,8 @@ export enum KnownScript { TypeBurnLock = "TypeBurnLock", EasyToDiscoverType = "EasyToDiscoverType", TimeLock = "TimeLock", + + // RGB++ related scripts (default using Bitcoin Testnet3) + RgbppLock = "RgbppLock", + BtcTimeLock = "BtcTimeLock", } From 1dad5dc18c176b398624e3cca6c39de1f33377f1 Mon Sep 17 00:00:00 2001 From: fgh Date: Tue, 30 Dec 2025 15:06:19 -0500 Subject: [PATCH 2/3] feat: add udt code of @ckb-ccc/rgbpp package --- packages/rgbpp/.prettierignore | 33 + packages/rgbpp/.prettierrc | 5 + packages/rgbpp/eslint.config.mjs | 62 + packages/rgbpp/package.json | 62 + packages/rgbpp/prettier.config.cjs | 11 + .../src/bitcoin/configs/script-manager.ts | 160 ++ .../src/bitcoin/configs/scripts/index.ts | 11 + packages/rgbpp/src/bitcoin/constants/index.ts | 25 + packages/rgbpp/src/bitcoin/types/address.ts | 12 + packages/rgbpp/src/bitcoin/types/network.ts | 18 + .../rgbpp/src/bitcoin/types/public-key.ts | 21 + .../rgbpp/src/bitcoin/types/rgbpp/rgbpp.ts | 176 ++ packages/rgbpp/src/bitcoin/types/rgbpp/udt.ts | 15 + packages/rgbpp/src/bitcoin/types/script.ts | 44 + .../rgbpp/src/bitcoin/types/transaction.ts | 67 + packages/rgbpp/src/bitcoin/utils/address.ts | 126 ++ packages/rgbpp/src/bitcoin/utils/common.ts | 13 + packages/rgbpp/src/bitcoin/utils/script.ts | 67 + .../rgbpp/src/bitcoin/utils/transaction.ts | 110 ++ packages/rgbpp/src/udt/index.ts | 219 +++ packages/rgbpp/src/utils/encoder.ts | 88 + packages/rgbpp/src/utils/rgbpp.ts | 235 +++ packages/rgbpp/src/utils/script.ts | 67 + packages/rgbpp/tsconfig.base.json | 22 + packages/rgbpp/tsconfig.commonjs.json | 8 + packages/rgbpp/tsconfig.json | 8 + pnpm-lock.yaml | 1591 +++++++++++++++-- 27 files changed, 3171 insertions(+), 105 deletions(-) create mode 100644 packages/rgbpp/.prettierignore create mode 100644 packages/rgbpp/.prettierrc create mode 100644 packages/rgbpp/eslint.config.mjs create mode 100644 packages/rgbpp/package.json create mode 100644 packages/rgbpp/prettier.config.cjs create mode 100644 packages/rgbpp/src/bitcoin/configs/script-manager.ts create mode 100644 packages/rgbpp/src/bitcoin/configs/scripts/index.ts create mode 100644 packages/rgbpp/src/bitcoin/constants/index.ts create mode 100644 packages/rgbpp/src/bitcoin/types/address.ts create mode 100644 packages/rgbpp/src/bitcoin/types/network.ts create mode 100644 packages/rgbpp/src/bitcoin/types/public-key.ts create mode 100644 packages/rgbpp/src/bitcoin/types/rgbpp/rgbpp.ts create mode 100644 packages/rgbpp/src/bitcoin/types/rgbpp/udt.ts create mode 100644 packages/rgbpp/src/bitcoin/types/script.ts create mode 100644 packages/rgbpp/src/bitcoin/types/transaction.ts create mode 100644 packages/rgbpp/src/bitcoin/utils/address.ts create mode 100644 packages/rgbpp/src/bitcoin/utils/common.ts create mode 100644 packages/rgbpp/src/bitcoin/utils/script.ts create mode 100644 packages/rgbpp/src/bitcoin/utils/transaction.ts create mode 100644 packages/rgbpp/src/udt/index.ts create mode 100644 packages/rgbpp/src/utils/encoder.ts create mode 100644 packages/rgbpp/src/utils/rgbpp.ts create mode 100644 packages/rgbpp/src/utils/script.ts create mode 100644 packages/rgbpp/tsconfig.base.json create mode 100644 packages/rgbpp/tsconfig.commonjs.json create mode 100644 packages/rgbpp/tsconfig.json diff --git a/packages/rgbpp/.prettierignore b/packages/rgbpp/.prettierignore new file mode 100644 index 000000000..611e372bf --- /dev/null +++ b/packages/rgbpp/.prettierignore @@ -0,0 +1,33 @@ +# Dependencies +node_modules +.pnp +.pnp.js + +# Testing +coverage +__snapshots__ + +# Production +build +dist +lib + +# Misc +.DS_Store +.env.local +.env.development.local +.env.test.local +.env.production.local + +# Debug logs +npm-debug.log* +yarn-debug.log* +yarn-error.log* + +# IDE +.idea +.vscode + +# Cache +.cache +.eslintcache diff --git a/packages/rgbpp/.prettierrc b/packages/rgbpp/.prettierrc new file mode 100644 index 000000000..6390af088 --- /dev/null +++ b/packages/rgbpp/.prettierrc @@ -0,0 +1,5 @@ +{ + "singleQuote": false, + "trailingComma": "all", + "plugins": ["prettier-plugin-organize-imports"] +} diff --git a/packages/rgbpp/eslint.config.mjs b/packages/rgbpp/eslint.config.mjs new file mode 100644 index 000000000..b6132c277 --- /dev/null +++ b/packages/rgbpp/eslint.config.mjs @@ -0,0 +1,62 @@ +// @ts-check + +import eslint from "@eslint/js"; +import eslintPluginPrettierRecommended from "eslint-plugin-prettier/recommended"; +import tseslint from "typescript-eslint"; + +import { dirname } from "path"; +import { fileURLToPath } from "url"; + +export default [ + ...tseslint.config({ + files: ["**/*.ts"], + extends: [ + eslint.configs.recommended, + ...tseslint.configs.recommendedTypeChecked, + ], + rules: { + "@typescript-eslint/no-unused-vars": [ + "error", + { + args: "all", + argsIgnorePattern: "^_", + caughtErrors: "all", + caughtErrorsIgnorePattern: "^_", + destructuredArrayIgnorePattern: "^_", + varsIgnorePattern: "^_", + ignoreRestSiblings: true, + }, + ], + "@typescript-eslint/unbound-method": ["error", { ignoreStatic: true }], + "@typescript-eslint/no-unsafe-member-access": "off", + "@typescript-eslint/require-await": "off", + "@typescript-eslint/only-throw-error": [ + "error", + { + allowThrowingAny: true, + allowThrowingUnknown: true, + allowRethrowing: true, + }, + ], + "@typescript-eslint/prefer-promise-reject-errors": [ + "error", + { + allowThrowingAny: true, + allowThrowingUnknown: true, + }, + ], + "no-empty": "off", + "prefer-const": [ + "error", + { ignoreReadBeforeAssign: true, destructuring: "all" }, + ], + }, + languageOptions: { + parserOptions: { + project: true, + tsconfigRootDir: dirname(fileURLToPath(import.meta.url)), + }, + }, + }), + eslintPluginPrettierRecommended, +]; diff --git a/packages/rgbpp/package.json b/packages/rgbpp/package.json new file mode 100644 index 000000000..5eca043de --- /dev/null +++ b/packages/rgbpp/package.json @@ -0,0 +1,62 @@ +{ + "name": "@ckb-ccc/rgbpp", + "version": "1.0.0", + "description": "RGB++ for CKB", + "types": "dist/index.d.ts", + "source": "src/index.ts", + "type": "module", + "main": "dist.commonjs/index.js", + "module": "dist/index.js", + "exports": { + ".": { + "import": "./dist/index.js", + "require": "./dist.commonjs/index.js", + "default": "./dist.commonjs/index.js" + } + }, + "scripts": { + "test": "jest", + "build": "rimraf ./dist && rimraf ./dist.commonjs && tsc && tsc --project tsconfig.commonjs.json && copyfiles -u 2 misc/basedirs/**/* .", + "lint": "eslint ./src", + "format": "prettier --write . && eslint --fix ./src" + }, + "keywords": [], + "author": "", + "license": "ISC", + "devDependencies": { + "@ckb-ccc/spore": "workspace:*", + "@ckb-ccc/udt": "workspace:*", + "@ckb-lumos/base": "^0.22.2", + "@ckb-lumos/codec": "^0.22.2", + "@eslint/js": "^9.34.0", + "@exact-realty/multipart-parser": "^1.0.13", + "@types/jest": "^29.5.14", + "@types/lodash": "^4.17.14", + "@types/node": "^22.10.6", + "copyfiles": "^2.4.1", + "dotenv": "^16.4.7", + "eslint": "^9.34.0", + "eslint-config-prettier": "^10.1.8", + "eslint-plugin-prettier": "^5.5.4", + "jest": "^29.7.0", + "prettier": "^3.6.2", + "prettier-plugin-organize-imports": "^4.2.0", + "rimraf": "^6.0.1", + "ts-jest": "^29.2.5", + "tsx": "^4.20.6", + "typescript": "^5.7.3", + "typescript-eslint": "^8.41.0" + }, + "dependencies": { + "@bitcoinerlab/secp256k1": "1.1.1", + "@ckb-ccc/core": "workspace:*", + "@ckb-lumos/base": "^0.23.0", + "@ckb-lumos/bi": "^0.23.0", + "@ckb-lumos/codec": "^0.23.0", + "bip32": "4.0.0", + "bitcoinjs-lib": "6.1.6", + "ecpair": "2.1.0", + "js-sha256": "^0.11.0", + "lodash": "^4.17.21" + } +} diff --git a/packages/rgbpp/prettier.config.cjs b/packages/rgbpp/prettier.config.cjs new file mode 100644 index 000000000..5e1810363 --- /dev/null +++ b/packages/rgbpp/prettier.config.cjs @@ -0,0 +1,11 @@ +/** + * @see https://prettier.io/docs/configuration + * @type {import("prettier").Config} + */ +const config = { + singleQuote: false, + trailingComma: "all", + plugins: [require.resolve("prettier-plugin-organize-imports")], +}; + +module.exports = config; diff --git a/packages/rgbpp/src/bitcoin/configs/script-manager.ts b/packages/rgbpp/src/bitcoin/configs/script-manager.ts new file mode 100644 index 000000000..89c2a2709 --- /dev/null +++ b/packages/rgbpp/src/bitcoin/configs/script-manager.ts @@ -0,0 +1,160 @@ +import { ccc } from "@ckb-ccc/core"; + +import { + buildBtcTimeLockArgs, + buildRgbppLockArgs, + buildUniqueTypeArgs, + pseudoRgbppLockArgs, +} from "../../utils/rgbpp.js"; +import { DEFAULT_CONFIRMATIONS } from "../constants/index.js"; +import { UtxoSeal } from "../types/rgbpp/rgbpp.js"; +import { IScriptProvider, RgbppScriptName } from "../types/script.js"; + +/** + * ScriptManager - Manages and builds RGB++ related scripts + * + * Uses IScriptProvider for flexible script source configuration. + * Supports multiple script sources through provider composition. + * + * @example + * ```typescript + * import { ScriptManager, ClientScriptProvider } from "@ckb-ccc/rgbpp"; + * + * // Basic usage with client + * const manager = new ScriptManager(new ClientScriptProvider(client)); + * + * // With custom scripts + * const manager = new ScriptManager( + * createScriptProvider(client, customScripts) + * ); + * ``` + */ +export class ScriptManager { + constructor(private provider: IScriptProvider) {} + + /** + * Get script info by name using the configured provider + * + * @param name - Known script name from ccc.KnownScript + * @returns ccc.ScriptInfo containing code hash, hash type, and cell dependencies + */ + async getKnownScriptInfo(name: ccc.KnownScript): Promise { + return this.provider.getScriptInfo(name); + } + + /** + * Get all required RGBPP script infos in one call + * This is a convenience method for initializing CkbRgbppUnlockSigner + * + * @returns Record containing RgbppLock, BtcTimeLock, and UniqueType script infos + * @example + * ```typescript + * const scriptInfos = await scriptManager.getRgbppScriptInfos(); + * const signer = new CkbRgbppUnlockSigner({ + * ckbClient, + * rgbppBtcAddress, + * btcDataSource, + * scriptInfos, + * }); + * ``` + */ + async getRgbppScriptInfos(): Promise< + Record + > { + const [rgbppLock, btcTimeLock, uniqueType] = await Promise.all([ + this.getKnownScriptInfo(ccc.KnownScript.RgbppLock), + this.getKnownScriptInfo(ccc.KnownScript.BtcTimeLock), + this.getKnownScriptInfo(ccc.KnownScript.UniqueType), + ]); + + return { + [ccc.KnownScript.RgbppLock]: rgbppLock, + [ccc.KnownScript.BtcTimeLock]: btcTimeLock, + [ccc.KnownScript.UniqueType]: uniqueType, + }; + } + + async buildPseudoRgbppLockScript(): Promise { + const scriptInfo = await this.getKnownScriptInfo(ccc.KnownScript.RgbppLock); + return ccc.Script.from({ + codeHash: scriptInfo.codeHash, + hashType: scriptInfo.hashType, + args: pseudoRgbppLockArgs(), + }); + } + + async buildRgbppLockScript(utxoSeal: UtxoSeal): Promise { + const scriptInfo = await this.getKnownScriptInfo(ccc.KnownScript.RgbppLock); + return ccc.Script.from({ + codeHash: scriptInfo.codeHash, + hashType: scriptInfo.hashType, + args: buildRgbppLockArgs({ + txId: utxoSeal.txId, + index: utxoSeal.index, // index in btc tx output + }), + }); + } + + async buildBtcTimeLockScript( + receiverLock: ccc.Script, + btcTxId: string, + confirmations = DEFAULT_CONFIRMATIONS, + ): Promise { + const scriptInfo = await this.getKnownScriptInfo( + ccc.KnownScript.BtcTimeLock, + ); + return ccc.Script.from({ + codeHash: scriptInfo.codeHash, + hashType: scriptInfo.hashType, + args: buildBtcTimeLockArgs(receiverLock, btcTxId, confirmations), + }); + } + + /* + https://github.com/nervosnetwork/rfcs/blob/master/rfcs/0022-transaction-structure/0022-transaction-structure.md#type-id + + There are two ways to create a new cell with a specific type id. + + 1. Create a transaction which uses any out point as tx.inputs[0] and has a output cell whose type script is Type ID. The output cell's type script args is the hash of tx.inputs[0] and its output index. Because any out point can only be used once as an input, tx.inputs[0] and thus the new type id must be different in each creation transaction. + 2. Destroy an old cell with a specific type id and create a new cell with the same type id in the same transaction. + */ + async buildUniqueTypeScript( + firstInput: ccc.CellInput, + outputIndex: number, + ): Promise { + const scriptInfo = await this.getKnownScriptInfo( + ccc.KnownScript.UniqueType, + ); + return ccc.Script.from({ + codeHash: scriptInfo.codeHash, + hashType: scriptInfo.hashType, + args: buildUniqueTypeArgs(firstInput, outputIndex), + }); + } + + /** + * Get RGB++ lock script template (without args) + */ + async rgbppLockScriptTemplate(): Promise { + const scriptInfo = await this.getKnownScriptInfo(ccc.KnownScript.RgbppLock); + return ccc.Script.from({ + codeHash: scriptInfo.codeHash, + hashType: scriptInfo.hashType, + args: "", + }); + } + + /** + * Get BTC time lock script template (without args) + */ + async btcTimeLockScriptTemplate(): Promise { + const scriptInfo = await this.getKnownScriptInfo( + ccc.KnownScript.BtcTimeLock, + ); + return ccc.Script.from({ + codeHash: scriptInfo.codeHash, + hashType: scriptInfo.hashType, + args: "", + }); + } +} diff --git a/packages/rgbpp/src/bitcoin/configs/scripts/index.ts b/packages/rgbpp/src/bitcoin/configs/scripts/index.ts new file mode 100644 index 000000000..1d0d27eff --- /dev/null +++ b/packages/rgbpp/src/bitcoin/configs/scripts/index.ts @@ -0,0 +1,11 @@ +import { ccc } from "@ckb-ccc/core"; +export const deadLock = ccc.Script.from({ + codeHash: + "0x0000000000000000000000000000000000000000000000000000000000000000", + hashType: "data", + args: "0x", +}); + +export const DEFAULT_DUST_LIMIT = 546; + +export const DEFAULT_FEE_RATE = 1; diff --git a/packages/rgbpp/src/bitcoin/constants/index.ts b/packages/rgbpp/src/bitcoin/constants/index.ts new file mode 100644 index 000000000..070a76e73 --- /dev/null +++ b/packages/rgbpp/src/bitcoin/constants/index.ts @@ -0,0 +1,25 @@ +import { sha256 } from "js-sha256"; + +const TX_ID_PLACEHOLDER_PRE_IMAGE = + "sha256 this for easy replacement in spore co-build witness"; +export const TX_ID_PLACEHOLDER = sha256(TX_ID_PLACEHOLDER_PRE_IMAGE); + +// https://github.com/utxostack/rgbpp/blob/main/contracts/rgbpp-lock/src/main.rs#L228 +export const BLANK_TX_ID = + "0000000000000000000000000000000000000000000000000000000000000000"; + +export const BTC_TX_PSEUDO_INDEX = 0xffffffff; // 4,294,967,295 (max u32) + +export const UNIQUE_TYPE_OUTPUT_INDEX = 1; + +export const DEFAULT_CONFIRMATIONS = 6; + +/** Default polling interval in milliseconds for waiting transaction confirmation */ +export const DEFAULT_CONFIRMATION_POLL_INTERVAL = 30_000; + +/** Default polling interval in milliseconds for SPV proof polling */ +export const DEFAULT_SPV_POLL_INTERVAL = 30_000; + +export const RGBPP_MAX_CELL_NUM = 255; + +export const RGBPP_UNLOCK_PARAMS_IDENTIFIER = "RGBPP_UNLOCK_PARAMS"; diff --git a/packages/rgbpp/src/bitcoin/types/address.ts b/packages/rgbpp/src/bitcoin/types/address.ts new file mode 100644 index 000000000..06f57b3da --- /dev/null +++ b/packages/rgbpp/src/bitcoin/types/address.ts @@ -0,0 +1,12 @@ +// Read more about the available address types: +// - P2WPKH: https://github.com/bitcoin/bips/blob/master/bip-0141.mediawiki#p2wpkh +// - P2TR: https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki +export enum AddressType { + P2PKH = "P2PKH", + P2WPKH = "P2WPKH", + P2TR = "P2TR", + P2SH_P2WPKH = "P2SH_P2WPKH", + P2WSH = "P2WSH", + P2SH = "P2SH", + UNKNOWN = "UNKNOWN", +} diff --git a/packages/rgbpp/src/bitcoin/types/network.ts b/packages/rgbpp/src/bitcoin/types/network.ts new file mode 100644 index 000000000..fe6348f6f --- /dev/null +++ b/packages/rgbpp/src/bitcoin/types/network.ts @@ -0,0 +1,18 @@ +export enum PredefinedNetwork { + BitcoinTestnet3 = "BitcoinTestnet3", + BitcoinMainnet = "BitcoinMainnet", +} + +export interface NetworkConfig { + name: string; + isMainnet: boolean; + btcDustLimit: number; + btcFeeRate: number; +} + +export interface NetworkConfigOverrides { + btcDustLimit?: number; + btcFeeRate?: number; +} + +export type Network = PredefinedNetwork | string; diff --git a/packages/rgbpp/src/bitcoin/types/public-key.ts b/packages/rgbpp/src/bitcoin/types/public-key.ts new file mode 100644 index 000000000..266d71fd6 --- /dev/null +++ b/packages/rgbpp/src/bitcoin/types/public-key.ts @@ -0,0 +1,21 @@ +import { AddressType } from "./address.js"; + +/** + * Public key provider interface + * Used to lookup public keys for addresses when building P2TR PSBT inputs + * + * @public + */ +export interface PublicKeyProvider { + /** + * Get the public key for a given address + * + * @param address - Bitcoin address + * @param addressType - Address type (e.g., P2TR, P2WPKH) + * @returns Public key in hex format (33-byte compressed or 32-byte x-only format), or undefined if not found + */ + getPublicKey( + address: string, + addressType: AddressType, + ): Promise; +} diff --git a/packages/rgbpp/src/bitcoin/types/rgbpp/rgbpp.ts b/packages/rgbpp/src/bitcoin/types/rgbpp/rgbpp.ts new file mode 100644 index 000000000..b9510bfa9 --- /dev/null +++ b/packages/rgbpp/src/bitcoin/types/rgbpp/rgbpp.ts @@ -0,0 +1,176 @@ +import { ccc, mol } from "@ckb-ccc/core"; + +export interface RgbppUdtToken { + decimal: number; + name: string; + symbol: string; +} + +export interface UtxoSeal { + txId: string; + index: number; +} + +// struct ExtraCommitmentData { +// input_len: byte, +// output_len: byte, +// } + +/** + * @public + */ +export type ExtraCommitmentDataLike = { + inputLen: ccc.NumLike; + outputLen: ccc.NumLike; +}; + +@mol.codec( + mol.struct({ + inputLen: mol.Uint8, + outputLen: mol.Uint8, + }), +) +export class ExtraCommitmentDataCCC extends mol.Entity.Base< + ExtraCommitmentDataLike, + ExtraCommitmentDataCCC +>() { + constructor( + public inputLen: ccc.Num, + public outputLen: ccc.Num, + ) { + super(); + } + + static from(ec: ExtraCommitmentDataLike): ExtraCommitmentDataCCC { + return new ExtraCommitmentDataCCC( + ccc.numFrom(ec.inputLen), + ccc.numFrom(ec.outputLen), + ); + } +} + +// table RGBPPUnlock { +// version: Uint16, +// extra_data: ExtraCommitmentData, +// btc_tx: Bytes, +// btc_tx_proof: Bytes, +// } + +/** + * @public + */ +export type RgbppUnlockLike = { + version: ccc.NumLike; + extraData: ExtraCommitmentDataLike; + btcTx: ccc.HexLike; + btcTxProof: ccc.HexLike; +}; +/** + * @public + */ +@mol.codec( + mol.table({ + version: mol.Uint16, + extraData: ExtraCommitmentDataCCC, + btcTx: mol.Bytes, + btcTxProof: mol.Bytes, + }), +) +export class RgbppUnlock extends mol.Entity.Base< + RgbppUnlockLike, + RgbppUnlock +>() { + constructor( + public version: ccc.Num, + public extraData: ExtraCommitmentDataCCC, + public btcTx: ccc.Hex, + public btcTxProof: ccc.Hex, + ) { + super(); + } + + static from(ru: RgbppUnlockLike): RgbppUnlock { + return new RgbppUnlock( + ccc.numFrom(ru.version), + ExtraCommitmentDataCCC.from(ru.extraData), + ccc.hexFrom(ru.btcTx), + ccc.hexFrom(ru.btcTxProof), + ); + } +} + +// table BTCTimeLock { +// lock_script: Script, +// after: Uint32, +// btc_txid: Byte32, +// } + +/** + * @public + */ +export type BtcTimeLockLike = { + lockScript: ccc.Script; + after: ccc.NumLike; + btcTxid: ccc.HexLike; +}; +/** + * @public + */ +@mol.codec( + mol.table({ + lockScript: ccc.Script, + after: mol.Uint32, + btcTxid: mol.Byte32, + }), +) +export class BtcTimeLock extends mol.Entity.Base< + BtcTimeLockLike, + BtcTimeLock +>() { + constructor( + public lockScript: ccc.Script, + public after: ccc.Num, + public btcTxid: string, + ) { + super(); + } + + static from(btl: BtcTimeLockLike): BtcTimeLock { + return new BtcTimeLock( + ccc.Script.from(btl.lockScript), + ccc.numFrom(btl.after), + ccc.hexFrom(btl.btcTxid), + ); + } +} + +// table BTCTimeUnlock { +// btc_tx_proof: Bytes, +// } + +/** + * @public + */ +export type BtcTimeUnlockLike = { + btcTxProof: ccc.HexLike; +}; +/** + * @public + */ +@mol.codec( + mol.table({ + btcTxProof: mol.Bytes, + }), +) +export class BtcTimeUnlock extends mol.Entity.Base< + BtcTimeUnlockLike, + BtcTimeUnlock +>() { + constructor(public btcTxProof: ccc.Hex) { + super(); + } + + static from(btul: BtcTimeUnlockLike): BtcTimeUnlock { + return new BtcTimeUnlock(ccc.hexFrom(btul.btcTxProof)); + } +} diff --git a/packages/rgbpp/src/bitcoin/types/rgbpp/udt.ts b/packages/rgbpp/src/bitcoin/types/rgbpp/udt.ts new file mode 100644 index 000000000..d10689053 --- /dev/null +++ b/packages/rgbpp/src/bitcoin/types/rgbpp/udt.ts @@ -0,0 +1,15 @@ +import { ccc } from "@ckb-ccc/core"; + +import { RgbppUdtToken } from "./rgbpp.js"; + +export interface RgbppUdtIssuance { + token: RgbppUdtToken; + amount: bigint; + rgbppLiveCells: ccc.Cell[]; + udtScriptInfo: ccc.ScriptInfo; +} + +export interface RgbppBtcReceiver { + address: string; + amount: bigint; +} diff --git a/packages/rgbpp/src/bitcoin/types/script.ts b/packages/rgbpp/src/bitcoin/types/script.ts new file mode 100644 index 000000000..3f6bf97ed --- /dev/null +++ b/packages/rgbpp/src/bitcoin/types/script.ts @@ -0,0 +1,44 @@ +import { ccc } from "@ckb-ccc/core"; + +/** + * Script provider interface + * Implement this interface to provide custom script sources + * + * Returns ccc.ScriptInfo which contains the script's code hash, hash type, and cell dependencies. + * + * @public + */ +export interface IScriptProvider { + getScriptInfo(name: ccc.KnownScript): Promise; +} + +/** + * Required RGBPP scripts that must be provided + * @public + */ +export const RGBPP_REQUIRED_SCRIPTS = [ + ccc.KnownScript.RgbppLock, + ccc.KnownScript.BtcTimeLock, + ccc.KnownScript.UniqueType, +] as const; + +/** + * Type representing the required RGBPP script names + * @public + */ +export type RgbppScriptName = (typeof RGBPP_REQUIRED_SCRIPTS)[number]; + +// Legacy types (kept for compatibility) +export interface ScriptSet { + [key: string]: ccc.Script; + [ccc.KnownScript.RgbppLock]: ccc.Script; + [ccc.KnownScript.BtcTimeLock]: ccc.Script; + [ccc.KnownScript.UniqueType]: ccc.Script; +} + +export interface CellDepSet { + [key: string]: ccc.CellDep; + [ccc.KnownScript.RgbppLock]: ccc.CellDep; + [ccc.KnownScript.BtcTimeLock]: ccc.CellDep; + [ccc.KnownScript.UniqueType]: ccc.CellDep; +} diff --git a/packages/rgbpp/src/bitcoin/types/transaction.ts b/packages/rgbpp/src/bitcoin/types/transaction.ts new file mode 100644 index 000000000..b1af40a22 --- /dev/null +++ b/packages/rgbpp/src/bitcoin/types/transaction.ts @@ -0,0 +1,67 @@ +import { AddressType } from "./address.js"; + +export interface BaseOutput { + txid: string; + vout: number; +} + +export interface Output extends BaseOutput { + value: number; + scriptPk: string; +} + +export interface Utxo extends Output { + addressType: AddressType; + address: string; + pubkey?: string; +} + +export interface BtcApiUtxoParams { + only_non_rgbpp_utxos?: boolean; + only_confirmed?: boolean; + min_satoshi?: number; + no_cache?: boolean; +} + +export interface BtcApiBalanceParams { + min_satoshi?: number; + no_cache?: boolean; +} + +export interface TxInputData { + hash: string; + index: number; + witnessUtxo: { value: number; script: Buffer }; + tapInternalKey?: Buffer; +} + +export type TxOutput = TxAddressOutput | TxScriptOutput; + +export interface TxBaseOutput { + value: number; + fixed?: boolean; + protected?: boolean; + minUtxoSatoshi?: number; +} + +export interface TxAddressOutput extends TxBaseOutput { + address: string; +} + +export interface TxScriptOutput extends TxBaseOutput { + script: Buffer; +} + +export type InitOutput = TxAddressOutput | TxDataOutput | TxScriptOutput; + +export interface TxDataOutput extends TxBaseOutput { + data: Buffer | string; +} + +export interface UtxoSealOptions { + targetValue?: number; + feeRate?: number; + btcUtxoParams?: BtcApiUtxoParams; + /** Polling interval in milliseconds for waiting transaction confirmation (default: 30000) */ + confirmationPollInterval?: number; +} diff --git a/packages/rgbpp/src/bitcoin/utils/address.ts b/packages/rgbpp/src/bitcoin/utils/address.ts new file mode 100644 index 000000000..7de84c708 --- /dev/null +++ b/packages/rgbpp/src/bitcoin/utils/address.ts @@ -0,0 +1,126 @@ +import * as bitcoin from "bitcoinjs-lib"; +import { AddressType } from "../types/address.js"; +import { PredefinedNetwork } from "../types/network.js"; + +export enum NetworkType { + MAINNET, + TESTNET, + REGTEST, // deprecated +} + +export function decodeAddress(address: string): { + networkType: NetworkType; + addressType: AddressType; +} { + const mainnet = bitcoin.networks.bitcoin; + const testnet = bitcoin.networks.testnet; + const regtest = bitcoin.networks.regtest; + let decodeBase58: bitcoin.address.Base58CheckResult; + let decodeBech32: bitcoin.address.Bech32Result; + let networkType: NetworkType | undefined; + let addressType: AddressType | undefined; + if ( + address.startsWith("bc1") || + address.startsWith("tb1") || + address.startsWith("bcrt1") + ) { + try { + decodeBech32 = bitcoin.address.fromBech32(address); + if (decodeBech32.prefix === mainnet.bech32) { + networkType = NetworkType.MAINNET; + } else if (decodeBech32.prefix === testnet.bech32) { + networkType = NetworkType.TESTNET; + } else if (decodeBech32.prefix === regtest.bech32) { + networkType = NetworkType.REGTEST; + } + if (decodeBech32.version === 0) { + if (decodeBech32.data.length === 20) { + addressType = AddressType.P2WPKH; + } else if (decodeBech32.data.length === 32) { + addressType = AddressType.P2WSH; + } + } else if (decodeBech32.version === 1) { + if (decodeBech32.data.length === 32) { + addressType = AddressType.P2TR; + } + } + if (networkType !== undefined && addressType !== undefined) { + return { + networkType, + addressType, + }; + } + } catch (_e) { + // Do nothing (no need to throw here) + } + } else { + try { + decodeBase58 = bitcoin.address.fromBase58Check(address); + if (decodeBase58.version === mainnet.pubKeyHash) { + networkType = NetworkType.MAINNET; + addressType = AddressType.P2PKH; + } else if (decodeBase58.version === testnet.pubKeyHash) { + networkType = NetworkType.TESTNET; + addressType = AddressType.P2PKH; + } else if (decodeBase58.version === regtest.pubKeyHash) { + // do not work + networkType = NetworkType.REGTEST; + addressType = AddressType.P2PKH; + } else if (decodeBase58.version === mainnet.scriptHash) { + networkType = NetworkType.MAINNET; + addressType = AddressType.P2SH_P2WPKH; + } else if (decodeBase58.version === testnet.scriptHash) { + networkType = NetworkType.TESTNET; + addressType = AddressType.P2SH_P2WPKH; + } else if (decodeBase58.version === regtest.scriptHash) { + // do not work + networkType = NetworkType.REGTEST; + addressType = AddressType.P2SH_P2WPKH; + } + + if (networkType !== undefined && addressType !== undefined) { + return { + networkType, + addressType, + }; + } + } catch (_e) { + // Do nothing (no need to throw here) + } + } + + return { + addressType: AddressType.UNKNOWN, + networkType: NetworkType.MAINNET, + }; +} + +export function getAddressType(address: string): AddressType { + return decodeAddress(address).addressType; +} + +export function parseAddressType( + addressType: AddressType | string, +): AddressType { + if (typeof addressType === "string") { + const type = AddressType[addressType as keyof typeof AddressType]; + if (!type) { + throw new Error(`Invalid address type: ${addressType}`); + } + return type; + } + + return addressType; +} + +export const SUPPORTED_ADDRESS_TYPES = [AddressType.P2WPKH, AddressType.P2TR]; + +export function isSupportedAddressType(at: AddressType): boolean { + return SUPPORTED_ADDRESS_TYPES.includes(at); +} + +export function toBtcNetwork(network: string): bitcoin.Network { + return network === (PredefinedNetwork.BitcoinMainnet as string) + ? bitcoin.networks.bitcoin + : bitcoin.networks.testnet; +} diff --git a/packages/rgbpp/src/bitcoin/utils/common.ts b/packages/rgbpp/src/bitcoin/utils/common.ts new file mode 100644 index 000000000..65aa33f25 --- /dev/null +++ b/packages/rgbpp/src/bitcoin/utils/common.ts @@ -0,0 +1,13 @@ +import { OutPoint } from "@ckb-ccc/core"; + +export function deduplicateByOutPoint( + items: T[], +): T[] { + const seen = new Set(); + return items.filter((item) => { + const key = `${item.outPoint.txHash}-${item.outPoint.index.toString()}`; + if (seen.has(key)) return false; + seen.add(key); + return true; + }); +} diff --git a/packages/rgbpp/src/bitcoin/utils/script.ts b/packages/rgbpp/src/bitcoin/utils/script.ts new file mode 100644 index 000000000..399240ddd --- /dev/null +++ b/packages/rgbpp/src/bitcoin/utils/script.ts @@ -0,0 +1,67 @@ +import * as bitcoin from "bitcoinjs-lib"; +import { trimHexPrefix } from "../../utils/encoder.js"; + +/** + * Convert data to OP_RETURN script pubkey. + * The data size should be ranged in 1 to 80 bytes. + * + * @example + * const data = Buffer.from('01020304', 'hex'); + * const scriptPk = dataToOpReturnScriptPubkey(data); // + * const scriptPkHex = scriptPk.toString('hex'); // 6a0401020304 + */ +export function dataToOpReturnScriptPubkey(data: Buffer | string): Buffer { + if (typeof data === "string") { + data = Buffer.from(trimHexPrefix(data), "hex"); + } + + const payment = bitcoin.payments.embed({ data: [data] }); + return payment.output!; +} + +/** + * Check if a script pubkey is an OP_RETURN script. + * + * A valid OP_RETURN script should have the following structure: + * - + * - + * + * @example + * // + * isOpReturnScriptPubkey(Buffer.from('6a0401020304', 'hex')); // true + * // + * isOpReturnScriptPubkey(Buffer.from('6a4c0f746573742d636f6d6d69746d656e74', 'hex')); // true + * // + * isOpReturnScriptPubkey(Buffer.from('6a4c', 'hex')); // false + * // + * isOpReturnScriptPubkey(Buffer.from('6a01', 'hex')); // false + * // ... (not an OP_RETURN script) + * isOpReturnScriptPubkey(Buffer.from('76a914a802fc56c704ce87c42d7c92eb75e7896bdc41e788ac', 'hex')); // false + */ +export function isOpReturnScriptPubkey(script: Buffer): boolean { + const scripts = bitcoin.script.decompile(script); + if (!scripts || scripts.length !== 2) { + return false; + } + + const [op, data] = scripts; + // OP_RETURN opcode is 0x6a in hex or 106 in integer + if (op !== bitcoin.opcodes.OP_RETURN) { + return false; + } + // Standard OP_RETURN data size is up to 80 bytes + if ( + !(data instanceof Buffer) || + data.byteLength < 1 || + data.byteLength > 80 + ) { + return false; + } + + // No false condition matched, it's an OP_RETURN script + return true; +} + +export function toXOnly(pubKey: Buffer): Buffer { + return pubKey.length === 32 ? pubKey : pubKey.subarray(1, 33); +} diff --git a/packages/rgbpp/src/bitcoin/utils/transaction.ts b/packages/rgbpp/src/bitcoin/utils/transaction.ts new file mode 100644 index 000000000..5e00824fa --- /dev/null +++ b/packages/rgbpp/src/bitcoin/utils/transaction.ts @@ -0,0 +1,110 @@ +import lodash from "lodash"; +import { trimHexPrefix } from "../../utils/encoder.js"; +import { AddressType } from "../types/address.js"; +import { PublicKeyProvider } from "../types/public-key.js"; +import { + InitOutput, + TxInputData, + TxOutput, + Utxo, +} from "../types/transaction.js"; +import { isSupportedAddressType, SUPPORTED_ADDRESS_TYPES } from "./address.js"; +import { + dataToOpReturnScriptPubkey, + isOpReturnScriptPubkey, + toXOnly, +} from "./script.js"; + +/** + * Convert UTXO to PSBT input data + * + * @param utxo - The UTXO to convert + * @param publicKeyProvider - Optional provider to lookup public keys for P2TR addresses + * @returns PSBT input data + * + * @throws Error if address type is unsupported or public key is missing for P2TR + */ +export async function utxoToInputData( + utxo: Utxo, + publicKeyProvider?: PublicKeyProvider, +): Promise { + if (!isSupportedAddressType(utxo.addressType)) { + throw new Error( + `Unsupported address type, only support ${SUPPORTED_ADDRESS_TYPES.join( + ", ", + )}`, + ); + } + + if (utxo.addressType === AddressType.P2WPKH) { + const data = { + hash: utxo.txid, + index: utxo.vout, + witnessUtxo: { + value: utxo.value, + script: Buffer.from(trimHexPrefix(utxo.scriptPk), "hex"), + }, + }; + return data; + } + + if (utxo.addressType === AddressType.P2TR) { + let pubkey = utxo.pubkey; + + if (!pubkey && publicKeyProvider) { + pubkey = await publicKeyProvider.getPublicKey( + utxo.address, + utxo.addressType, + ); + } + + if (!pubkey) { + throw new Error( + `Missing pubkey for P2TR address ${utxo.address}. ` + + `Please provide a PublicKeyProvider or add pubkey to UTXO data.`, + ); + } + + const data = { + hash: utxo.txid, + index: utxo.vout, + witnessUtxo: { + value: utxo.value, + script: Buffer.from(trimHexPrefix(utxo.scriptPk), "hex"), + }, + tapInternalKey: toXOnly(Buffer.from(trimHexPrefix(pubkey), "hex")), + }; + return data; + } + + throw new Error("Unsupported address type"); +} + +export function convertToOutput(output: InitOutput): TxOutput { + let result: TxOutput | undefined; + + if ("data" in output) { + result = { + script: dataToOpReturnScriptPubkey(output.data), + value: output.value, + fixed: output.fixed, + protected: output.protected, + minUtxoSatoshi: output.minUtxoSatoshi, + }; + } + if ("address" in output || "script" in output) { + result = lodash.cloneDeep(output); + } + if (!result) { + throw new Error("Unsupported output"); + } + + const minUtxoSatoshi = 546; + const isOpReturnOutput = + "script" in result && isOpReturnScriptPubkey(result.script); + if (!isOpReturnOutput && result.value < minUtxoSatoshi) { + throw new Error("value is less than minUtxoSatoshi"); + } + + return result; +} diff --git a/packages/rgbpp/src/udt/index.ts b/packages/rgbpp/src/udt/index.ts new file mode 100644 index 000000000..d03c8f94c --- /dev/null +++ b/packages/rgbpp/src/udt/index.ts @@ -0,0 +1,219 @@ +import { ccc } from "@ckb-ccc/core"; + +import { + TX_ID_PLACEHOLDER, + UNIQUE_TYPE_OUTPUT_INDEX, +} from "../bitcoin/constants/index.js"; + +import { ScriptManager } from "../bitcoin/configs/script-manager.js"; +import { deadLock } from "../bitcoin/configs/scripts/index.js"; +import { NetworkConfig } from "../bitcoin/types/network.js"; +import { UtxoSeal } from "../bitcoin/types/rgbpp/rgbpp.js"; +import { RgbppUdtIssuance } from "../bitcoin/types/rgbpp/udt.js"; +import { IScriptProvider, RgbppScriptName } from "../bitcoin/types/script.js"; +import { deduplicateByOutPoint } from "../bitcoin/utils/common.js"; +import { u128ToLe } from "../utils/encoder.js"; +import { encodeRgbppUdtToken } from "../utils/rgbpp.js"; +import { + isUsingOneOfScripts, + updateScriptArgsWithTxId, +} from "../utils/script.js"; + +export class RgbppUdtClient { + public scriptManager: ScriptManager; + + constructor( + _networkConfig: NetworkConfig, + private ckbClient: ccc.Client, + scriptProvider: IScriptProvider, + ) { + this.scriptManager = new ScriptManager(scriptProvider); + } + + async rgbppLockScriptTemplate(): Promise { + return this.scriptManager.rgbppLockScriptTemplate(); + } + + async btcTimeLockScriptTemplate(): Promise { + return this.scriptManager.btcTimeLockScriptTemplate(); + } + + async buildRgbppLockScript(utxoSeal: UtxoSeal): Promise { + return this.scriptManager.buildRgbppLockScript(utxoSeal); + } + + async buildPseudoRgbppLockScript(): Promise { + return this.scriptManager.buildPseudoRgbppLockScript(); + } + + async buildBtcTimeLockScript( + ckbAddress: string, + confirmations?: number, + ): Promise { + const receiverLock = ( + await ccc.Address.fromString(ckbAddress, this.ckbClient) + ).script; + + return this.scriptManager.buildBtcTimeLockScript( + receiverLock, + TX_ID_PLACEHOLDER, + confirmations, + ); + } + + async getRgbppScriptInfos(): Promise< + Record + > { + const [rgbppLock, btcTimeLock, uniqueType] = await Promise.all([ + this.scriptManager.getKnownScriptInfo(ccc.KnownScript.RgbppLock), + this.scriptManager.getKnownScriptInfo(ccc.KnownScript.BtcTimeLock), + this.scriptManager.getKnownScriptInfo(ccc.KnownScript.UniqueType), + ]); + + return { + [ccc.KnownScript.RgbppLock]: rgbppLock, + [ccc.KnownScript.BtcTimeLock]: btcTimeLock, + [ccc.KnownScript.UniqueType]: uniqueType, + } as Record; + } + + // * It's assumed that all the tx.outputs are rgbpp/btc time lock scripts. + injectTxIdToRgbppCkbTx = async ( + tx: ccc.Transaction, + txId: string, + ): Promise => { + const rgbppLockTemplate = await this.rgbppLockScriptTemplate(); + const btcTimeLockTemplate = await this.btcTimeLockScriptTemplate(); + + const outputs = tx.outputs.map((output, _index) => { + if ( + !isUsingOneOfScripts(output.lock, [ + rgbppLockTemplate, + btcTimeLockTemplate, + ]) + ) { + throw new Error( + `Invalid output lock, expected one of rgbpp/btc time lock scripts, but got ${output.lock.codeHash}`, + ); + } + + return ccc.CellOutput.from({ + ...output, + lock: { + ...output.lock, + args: updateScriptArgsWithTxId(output.lock.args, txId), + }, + }); + }); + + return ccc.Transaction.from({ + ...tx, + outputs, + }); + }; + + async createRgbppUdtIssuanceCells( + signer: ccc.Signer, + utxoSeal: UtxoSeal, + ): Promise { + const rgbppLockScript = await this.buildRgbppLockScript(utxoSeal); + + const rgbppCellsGen = signer.client.findCellsByLock(rgbppLockScript); + const rgbppCells: ccc.Cell[] = []; + for await (const cell of rgbppCellsGen) { + rgbppCells.push(cell); + } + + if (rgbppCells.length !== 0) { + console.log("Using existing RGB++ cell"); + return rgbppCells; + } + + console.log("RGB++ cell not found, creating a new one"); + const tx = ccc.Transaction.default(); + + // If additional capacity is required when used as an input in a transaction, it can always be supplemented in `completeInputsByCapacity`. + tx.addOutput({ + lock: rgbppLockScript, + }); + + await tx.completeInputsByCapacity(signer); + await tx.completeFeeBy(signer); + const txHash = await signer.sendTransaction(tx); + await signer.client.waitTransaction(txHash); + console.log(`RGB++ cell created, txHash: ${txHash}`); + + const cell = await signer.client.getCellLive({ + txHash, + index: 0, + }); + if (!cell) { + throw new Error("Cell not found"); + } + + return [cell]; + } + + async issuanceCkbPartialTx( + params: RgbppUdtIssuance, + ): Promise { + if (params.rgbppLiveCells.length === 0) { + throw new Error("rgbppLiveCells is empty"); + } + + const rgpbbLiveCells = deduplicateByOutPoint(params.rgbppLiveCells); + + const tx = ccc.Transaction.default(); + await Promise.all( + rgpbbLiveCells.map(async (cell) => { + const cellInput = ccc.CellInput.from({ + previousOutput: cell.outPoint, + }); + await cellInput.completeExtraInfos(this.ckbClient); + + tx.inputs.push(cellInput); + }), + ); + + const pseudoRgbppLock = + await this.scriptManager.buildPseudoRgbppLockScript(); + const btcTimeLock = await this.scriptManager.buildBtcTimeLockScript( + deadLock, + TX_ID_PLACEHOLDER, + ); + const uniqueType = await this.scriptManager.buildUniqueTypeScript( + tx.inputs[0], + UNIQUE_TYPE_OUTPUT_INDEX, + ); + const uniqueTypeInfo = await this.scriptManager.getKnownScriptInfo( + ccc.KnownScript.UniqueType, + ); + + tx.addOutput( + { + lock: pseudoRgbppLock, + type: ccc.Script.from({ + codeHash: params.udtScriptInfo.codeHash, + hashType: params.udtScriptInfo.hashType, + args: params.rgbppLiveCells[0].cellOutput.lock.hash(), // unique ID of udt token + }), + }, + u128ToLe(params.amount * BigInt(10 ** params.token.decimal)), + ); + + tx.addOutput( + { + lock: btcTimeLock, + type: uniqueType, + }, + encodeRgbppUdtToken(params.token), + ); + + tx.addCellDeps( + params.udtScriptInfo.cellDeps[0].cellDep, + uniqueTypeInfo.cellDeps[0].cellDep, + ); + + return tx; + } +} diff --git a/packages/rgbpp/src/utils/encoder.ts b/packages/rgbpp/src/utils/encoder.ts new file mode 100644 index 000000000..91ee049cb --- /dev/null +++ b/packages/rgbpp/src/utils/encoder.ts @@ -0,0 +1,88 @@ +import { Hex, hexFrom } from "@ckb-ccc/core"; + +export const trimHexPrefix = (hex: string): string => + hex.startsWith("0x") ? hex.substring(2) : hex; + +export const prependHexPrefix = (hex: string): Hex => + (hex.startsWith("0x") ? hex : `0x${hex}`) as Hex; + +export const u8ToHex = (u8: number): Hex => { + if (u8 < 0 || u8 > 255 || !Number.isInteger(u8)) { + throw new Error("Input must be an integer between 0 and 255"); + } + return prependHexPrefix(u8.toString(16).padStart(2, "0")); +}; + +export const u32ToHex = (u32: string | number, littleEndian = false): Hex => { + const num = Number(u32); + if (num < 0 || num > 0xffffffff || !Number.isInteger(num)) { + throw new Error("Input must be an unsigned 32-bit integer"); + } + + const hex = num.toString(16).padStart(8, "0"); + return littleEndian ? reverseHexByteOrder(hex as Hex) : prependHexPrefix(hex); +}; + +export const utf8ToHex = (text: string): Hex => { + const result = text.trim(); + if (result.startsWith("0x")) { + return result as Hex; + } + return hexFrom(new TextEncoder().encode(result)); +}; + +export const reverseHexByteOrder = (hex: Hex): Hex => { + const trimmed = trimHexPrefix(hex); + const pairs = trimmed.match(/.{2}/g) || []; + return prependHexPrefix(pairs.reverse().join("")); +}; + +export const u128ToLe = (u128: bigint): string => { + if (u128 < 0n || u128 > 0xffffffffffffffffffffffffffffffffn) { + throw new Error("Input must be an unsigned 128-bit integer"); + } + + const buffer = Buffer.alloc(16); + for (let i = 0; i < 16; i++) { + buffer[i] = Number((u128 >> BigInt(i * 8)) & 0xffn); + } + + return buffer.toString("hex"); +}; + +export function leToU128(le: string): bigint { + const trimmedLe = trimHexPrefix(le); + if (!/^[0-9a-fA-F]+$/.test(trimmedLe)) { + throw new Error("Input must be a valid hex string"); + } + const paddedLe = trimmedLe.padStart(32, "0"); + + const beHex = paddedLe.match(/.{2}/g)?.reverse().join("") || ""; + return BigInt(`0x${beHex}`); +} + +export const u64ToLe = (u64: bigint): string => { + if (u64 < 0n || u64 > 0xffffffffffffffffn) { + throw new Error("Input must be an unsigned 64-bit integer"); + } + + const buffer = Buffer.alloc(8); + for (let i = 0; i < 8; i++) { + buffer[i] = Number((u64 >> BigInt(i * 8)) & 0xffn); + } + + return buffer.toString("hex"); +}; + +export const u32ToLe = (u32: number): string => { + if (u32 < 0 || u32 > 0xffffffff || !Number.isInteger(u32)) { + throw new Error("Input must be an unsigned 32-bit integer"); + } + + const buffer = Buffer.alloc(4); + for (let i = 0; i < 4; i++) { + buffer[i] = (u32 >> (i * 8)) & 0xff; + } + + return buffer.toString("hex"); +}; diff --git a/packages/rgbpp/src/utils/rgbpp.ts b/packages/rgbpp/src/utils/rgbpp.ts new file mode 100644 index 000000000..44a8f8fc6 --- /dev/null +++ b/packages/rgbpp/src/utils/rgbpp.ts @@ -0,0 +1,235 @@ +import { sha256 } from "js-sha256"; + +import { ccc } from "@ckb-ccc/core"; + +import { InitOutput, TxOutput } from "../bitcoin/types/transaction.js"; +import { convertToOutput } from "../bitcoin/utils/transaction.js"; + +import { + BLANK_TX_ID, + BTC_TX_PSEUDO_INDEX, + DEFAULT_CONFIRMATIONS, + RGBPP_MAX_CELL_NUM, + TX_ID_PLACEHOLDER, +} from "../bitcoin/constants/index.js"; + +import { + BtcTimeLock, + RgbppUdtToken, + RgbppUnlock, + UtxoSeal, +} from "../bitcoin/types/rgbpp/rgbpp.js"; +import { RgbppUdtClient } from "../udt/index.js"; +import { isSameScriptTemplate, isUsingOneOfScripts } from "../utils/script.js"; +import { + prependHexPrefix, + reverseHexByteOrder, + trimHexPrefix, + u32ToHex, + u32ToLe, + u64ToLe, + u8ToHex, + utf8ToHex, +} from "./encoder.js"; + +export const encodeRgbppUdtToken = (token: RgbppUdtToken): string => { + const decimal = u8ToHex(token.decimal); + const name = trimHexPrefix(utf8ToHex(token.name)); + const nameSize = trimHexPrefix(u8ToHex(name.length / 2)); + const symbol = trimHexPrefix(utf8ToHex(token.symbol)); + const symbolSize = trimHexPrefix(u8ToHex(symbol.length / 2)); + return `${decimal}${nameSize}${name}${symbolSize}${symbol}`; +}; + +/** + * https://learnmeabitcoin.com/technical/general/byte-order/ + * Whenever you're working with transaction/block hashes internally (e.g. inside raw bitcoin data), you use the natural byte order. + * Whenever you're displaying or searching for transaction/block hashes, you use the reverse byte order. + */ +export const buildRgbppLockArgs = (utxoSeal: UtxoSeal): ccc.Hex => { + return prependHexPrefix( + `${u32ToHex(utxoSeal.index, true)}${btcTxIdInReverseByteOrder( + utxoSeal.txId, + )}`, + ); +}; + +export function btcTxIdInReverseByteOrder(btcTxId: string): string { + return trimHexPrefix(reverseHexByteOrder(prependHexPrefix(btcTxId))); +} + +export function pseudoRgbppLockArgs(): ccc.Hex { + return buildRgbppLockArgs({ + txId: TX_ID_PLACEHOLDER, + index: BTC_TX_PSEUDO_INDEX, + }); +} + +export function pseudoRgbppLockArgsForCommitment(index: number): ccc.Hex { + return buildRgbppLockArgs({ + txId: BLANK_TX_ID, + index, + }); +} + +export const buildBtcTimeLockArgs = ( + receiverLock: ccc.Script, + btcTxId: string, + confirmations = DEFAULT_CONFIRMATIONS, +): ccc.Hex => { + return ccc.hexFrom( + BtcTimeLock.encode({ + lockScript: receiverLock, + after: confirmations, + btcTxid: reverseHexByteOrder(prependHexPrefix(btcTxId)), + }), + ); +}; + +export const buildUniqueTypeArgs = ( + firstInput: ccc.CellInput, + firstOutputIndex: number, +) => { + const input = ccc.bytesFrom(firstInput.toBytes()); + const s = new ccc.HasherCkb(); + s.update(input); + s.update(ccc.bytesFrom(prependHexPrefix(u64ToLe(BigInt(firstOutputIndex))))); + return s.digest().slice(0, 42); +}; + +export const buildRgbppUnlock = ( + btcLikeTxBytes: string, + btcLikeTxProof: ccc.Hex, + inputLen: number, + outputLen: number, +) => { + return ccc.hexFrom( + RgbppUnlock.encode({ + version: 0, + extraData: { + inputLen, + outputLen, + }, + btcTx: prependHexPrefix(btcLikeTxBytes), + btcTxProof: prependHexPrefix(btcLikeTxProof), + }), + ); +}; + +// The maximum length of inputs and outputs is 255, and the field type representing the length in the RGB++ protocol is Uint8 +// refer to https://github.com/ckb-cell/rgbpp/blob/0c090b039e8d026aad4336395b908af283a70ebf/contracts/rgbpp-lock/src/main.rs#L173-L211 +export const calculateCommitment = (ckbPartialTx: ccc.Transaction): string => { + const hash = sha256.create(); + hash.update(ccc.bytesFrom(utf8ToHex("RGB++"))); + const version = [0, 0]; + hash.update(version); + + const { inputs, outputs, outputsData } = ckbPartialTx; + + if ( + inputs.length > RGBPP_MAX_CELL_NUM || + outputs.length > RGBPP_MAX_CELL_NUM + ) { + throw new Error( + "The inputs or outputs length of RGB++ CKB virtual tx cannot be greater than 255", + ); + } + hash.update([inputs.length, outputs.length]); + + for (const input of inputs) { + hash.update(ccc.bytesFrom(input.previousOutput.toBytes())); + } + for (let index = 0; index < outputs.length; index++) { + const outputData = outputsData[index]; + hash.update(ccc.bytesFrom(outputs[index].toBytes())); + + const outputDataLen = u32ToLe(trimHexPrefix(outputData).length / 2); + const odl = ccc.bytesFrom(prependHexPrefix(outputDataLen)); + const od = ccc.bytesFrom(outputData); + hash.update(odl); + hash.update(od); + } + // double sha256 + return sha256(hash.array()); +}; + +export const isCommitmentMatched = ( + commitment: string, + ckbPartialTx: ccc.Transaction, + lastCkbTypedOutputIndex: number, +): boolean => { + return ( + commitment === + calculateCommitment( + ccc.Transaction.from({ + inputs: ckbPartialTx.inputs, + outputs: ckbPartialTx.outputs.slice(0, lastCkbTypedOutputIndex + 1), + outputsData: ckbPartialTx.outputsData.slice( + 0, + lastCkbTypedOutputIndex + 1, + ), + }), + ) + ); +}; + +// RGB++ related outputs +export const buildBtcRgbppOutputs = async ( + ckbPartialTx: ccc.Transaction, + btcChangeAddress: string, + receiverBtcAddresses: string[], + btcDustLimit: number, + rgbppUdtClient: RgbppUdtClient, +): Promise => { + const commitment = calculateCommitment(ckbPartialTx); + + const rgbppLockScriptTemplate = + await rgbppUdtClient.rgbppLockScriptTemplate(); + const btcTimeLockScriptTemplate = + await rgbppUdtClient.btcTimeLockScriptTemplate(); + + const outputs: InitOutput[] = []; + let lastCkbTypedOutputIndex = -1; + ckbPartialTx.outputs.forEach((output, index) => { + // If output.type is not null, then the output.lock must be RGB++ Lock or BTC Time Lock + if (output.type) { + if ( + !isUsingOneOfScripts(output.lock, [ + rgbppLockScriptTemplate, + btcTimeLockScriptTemplate, + ]) + ) { + throw new Error("Invalid cell lock"); + } + lastCkbTypedOutputIndex = index; + } + + // If output.lock is RGB++ Lock, generate a corresponding output in outputs + if (isSameScriptTemplate(output.lock, rgbppLockScriptTemplate)) { + outputs.push({ + fixed: true, + // Out-of-range index indicates this is a RGB++ change output returning to the BTC address + address: receiverBtcAddresses[index] ?? btcChangeAddress, + value: btcDustLimit, + minUtxoSatoshi: btcDustLimit, + }); + } + }); + + if (lastCkbTypedOutputIndex < 0) { + throw new Error("Invalid outputs"); + } + + if (!isCommitmentMatched(commitment, ckbPartialTx, lastCkbTypedOutputIndex)) { + throw new Error("Commitment mismatch"); + } + + // place the commitment as the first output + outputs.unshift({ + data: commitment, + value: 0, + fixed: true, + }); + + return outputs.map((output) => convertToOutput(output)); +}; diff --git a/packages/rgbpp/src/utils/script.ts b/packages/rgbpp/src/utils/script.ts new file mode 100644 index 000000000..5a8d63329 --- /dev/null +++ b/packages/rgbpp/src/utils/script.ts @@ -0,0 +1,67 @@ +import { ccc } from "@ckb-ccc/core"; + +import { UtxoSeal } from "../bitcoin/types/rgbpp/rgbpp.js"; +import { + prependHexPrefix, + reverseHexByteOrder, + trimHexPrefix, +} from "./encoder.js"; + +export const isSameScriptTemplate = ( + lock1: ccc.Script, + lock2: ccc.Script, +): boolean => { + return lock1.codeHash === lock2.codeHash && lock1.hashType === lock2.hashType; +}; + +export const isUsingOneOfScripts = ( + script: ccc.Script, + scripts: ccc.Script[], +): boolean => { + return ( + scripts.length > 0 && scripts.some((s) => isSameScriptTemplate(s, script)) + ); +}; + +export const updateScriptArgsWithTxId = ( + args: ccc.Hex, + txId: string, +): string => { + const argsLength = trimHexPrefix(args).length; + if (argsLength < (32 + 2) * 2) { + throw new Error("Lock args length is invalid"); + } + return prependHexPrefix( + `${trimHexPrefix(args).substring(0, argsLength - 32 * 2)}${trimHexPrefix( + reverseHexByteOrder(prependHexPrefix(txId)), + )}`, + ); +}; + +export function getTxIdFromScriptArgs(args: ccc.Hex): string { + if (args.length < 32 * 2) { + throw new Error("Lock args length is invalid"); + } + + return trimHexPrefix( + reverseHexByteOrder(args.substring(args.length - 32 * 2) as ccc.Hex), + ); +} + +export function getTxIndexFromScriptArgs(args: ccc.Hex): number { + if (args.length < 32 * 2) { + throw new Error("Lock args length is invalid"); + } + + return parseInt( + reverseHexByteOrder(trimHexPrefix(args.substring(0, 8)) as ccc.Hex), + 16, + ); +} + +export function parseUtxoSealFromScriptArgs(args: ccc.Hex): UtxoSeal { + return { + txId: getTxIdFromScriptArgs(args), + index: getTxIndexFromScriptArgs(args), + }; +} diff --git a/packages/rgbpp/tsconfig.base.json b/packages/rgbpp/tsconfig.base.json new file mode 100644 index 000000000..7e5ac952b --- /dev/null +++ b/packages/rgbpp/tsconfig.base.json @@ -0,0 +1,22 @@ +{ + "compilerOptions": { + "target": "es2020", + "incremental": true, + "allowJs": true, + "importHelpers": false, + "declaration": true, + "declarationMap": true, + "experimentalDecorators": true, + "useDefineForClassFields": false, + "esModuleInterop": true, + "strict": true, + "noImplicitAny": true, + "strictBindCallApply": true, + "strictNullChecks": true, + "alwaysStrict": true, + "noFallthroughCasesInSwitch": true, + "forceConsistentCasingInFileNames": true, + "skipLibCheck": true + }, + "include": ["src/**/*"] +} diff --git a/packages/rgbpp/tsconfig.commonjs.json b/packages/rgbpp/tsconfig.commonjs.json new file mode 100644 index 000000000..76a25e98b --- /dev/null +++ b/packages/rgbpp/tsconfig.commonjs.json @@ -0,0 +1,8 @@ +{ + "extends": "./tsconfig.base.json", + "compilerOptions": { + "module": "NodeNext", + "moduleResolution": "NodeNext", + "outDir": "./dist.commonjs" + } +} diff --git a/packages/rgbpp/tsconfig.json b/packages/rgbpp/tsconfig.json new file mode 100644 index 000000000..16f78d28a --- /dev/null +++ b/packages/rgbpp/tsconfig.json @@ -0,0 +1,8 @@ +{ + "extends": "./tsconfig.base.json", + "compilerOptions": { + "module": "ESNext", + "moduleResolution": "Bundler", + "outDir": "./dist" + } +} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 7fa2ac90a..d57ac3698 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -24,7 +24,7 @@ importers: version: 30.0.0 '@vitest/coverage-v8': specifier: 3.2.4 - version: 3.2.4(vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1)) + version: 3.2.4(vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1)) jest: specifier: 30.1.1 version: 30.1.1(@types/node@24.3.0)(ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2)) @@ -48,7 +48,7 @@ importers: version: 5.9.2 vitest: specifier: ^3.2.4 - version: 3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1) + version: 3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1) packages/ccc: dependencies: @@ -296,7 +296,7 @@ importers: version: 8.41.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) vitest: specifier: ^3.2.4 - version: 3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1) + version: 3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1) packages/demo: dependencies: @@ -378,7 +378,7 @@ importers: version: 9.34.0(jiti@2.5.1) eslint-config-next: specifier: 16.0.10 - version: 16.0.10(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) + version: 16.0.10(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) eslint-config-prettier: specifier: ^10.1.8 version: 10.1.8(eslint@9.34.0(jiti@2.5.1)) @@ -948,6 +948,100 @@ importers: specifier: ^8.41.0 version: 8.41.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) + packages/rgbpp: + dependencies: + '@bitcoinerlab/secp256k1': + specifier: 1.1.1 + version: 1.1.1 + '@ckb-ccc/core': + specifier: workspace:* + version: link:../core + '@ckb-lumos/base': + specifier: ^0.23.0 + version: 0.23.0 + '@ckb-lumos/bi': + specifier: ^0.23.0 + version: 0.23.0 + '@ckb-lumos/codec': + specifier: ^0.23.0 + version: 0.23.0 + bip32: + specifier: 4.0.0 + version: 4.0.0 + bitcoinjs-lib: + specifier: 6.1.6 + version: 6.1.6 + ecpair: + specifier: 2.1.0 + version: 2.1.0 + js-sha256: + specifier: ^0.11.0 + version: 0.11.1 + lodash: + specifier: ^4.17.21 + version: 4.17.21 + devDependencies: + '@ckb-ccc/spore': + specifier: workspace:* + version: link:../spore + '@ckb-ccc/udt': + specifier: workspace:* + version: link:../udt + '@eslint/js': + specifier: ^9.34.0 + version: 9.34.0 + '@exact-realty/multipart-parser': + specifier: ^1.0.13 + version: 1.0.14 + '@types/jest': + specifier: ^29.5.14 + version: 29.5.14 + '@types/lodash': + specifier: ^4.17.14 + version: 4.17.20 + '@types/node': + specifier: ^22.10.6 + version: 22.19.3 + copyfiles: + specifier: ^2.4.1 + version: 2.4.1 + dotenv: + specifier: ^16.4.7 + version: 16.4.7 + eslint: + specifier: ^9.34.0 + version: 9.34.0(jiti@2.5.1) + eslint-config-prettier: + specifier: ^10.1.8 + version: 10.1.8(eslint@9.34.0(jiti@2.5.1)) + eslint-plugin-prettier: + specifier: ^5.5.4 + version: 5.5.4(@types/eslint@9.6.1)(eslint-config-prettier@10.1.8(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1))(prettier@3.6.2) + jest: + specifier: ^29.7.0 + version: 29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + prettier: + specifier: ^3.6.2 + version: 3.6.2 + prettier-plugin-organize-imports: + specifier: ^4.2.0 + version: 4.2.0(prettier@3.6.2)(typescript@5.9.2) + rimraf: + specifier: ^6.0.1 + version: 6.0.1 + ts-jest: + specifier: ^29.2.5 + version: 29.4.1(@babel/core@7.28.3)(@jest/transform@30.1.1)(@jest/types@30.0.5)(babel-jest@30.1.1(@babel/core@7.28.3))(jest-util@30.0.5)(jest@29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)))(typescript@5.9.2) + tsx: + specifier: ^4.20.6 + version: 4.21.0 + typescript: + specifier: ^5.7.3 + version: 5.9.2 + typescript-eslint: + specifier: ^8.41.0 + version: 8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) + packages/shell: dependencies: '@ckb-ccc/core': @@ -1041,7 +1135,7 @@ importers: version: 8.41.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) vitest: specifier: ^3.2.4 - version: 3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1) + version: 3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1) packages/ssri: dependencies: @@ -2044,6 +2138,9 @@ packages: resolution: {integrity: sha512-6zABk/ECA/QYSCQ1NGiVwwbQerUCZ+TQbp64Q3AgmfNvurHH0j8TtXa1qbShXA6qqkpAj4V5W8pP6mLe1mcMqA==} engines: {node: '>=18'} + '@bitcoinerlab/secp256k1@1.1.1': + resolution: {integrity: sha512-uhjW51WfVLpnHN7+G0saDcM/k9IqcyTbZ+bDgLF3AX8V/a3KXSE9vn7UPBrcdU72tp0J4YPR7BHp2m7MLAZ/1Q==} + '@borewit/text-codec@0.1.1': resolution: {integrity: sha512-5L/uBxmjaCIX5h8Z+uu+kA9BQLkc/Wl06UGR5ajNRxu+/XjonB5i8JpgFMrPj3LXTCPA0pv8yxUvbUi+QthGGA==} @@ -2108,10 +2205,18 @@ packages: '@changesets/write@0.4.0': resolution: {integrity: sha512-CdTLvIOPiCNuH71pyDu3rA+Q0n65cmAbXnwWH84rKGiFumFzkmHNT8KHTMEchcxN+Kl8I54xGUhJ7l3E7X396Q==} + '@ckb-lumos/base@0.23.0': + resolution: {integrity: sha512-8aLFsUyWIK0rT7GQlYFuXyiG5lQ2bLRK2GvUsxv5G7I3nJ1UyxjwvVOdtlsR/cwhzOam3ujwqASqBIayBL6GLA==} + engines: {node: '>=12.0.0'} + '@ckb-lumos/base@0.24.0-next.2': resolution: {integrity: sha512-VCXYpykJ+OhjbcCp3imwt9rk3Ie2T8jyCjSXExkoyKY+QT+EI856p37KBbBdO4r7gguVtADnJS+WLIZoNm5Bvw==} engines: {node: '>=12.0.0'} + '@ckb-lumos/bi@0.23.0': + resolution: {integrity: sha512-KAy+lyVpL+Al4XD+c9tHrA9DSpHkMusyXtTS81aNZi5MyL6F9jrVmFcqLorhfyfl8Fsv2sEjMe5Neo2Y+w/RJQ==} + engines: {node: '>=12.0.0'} + '@ckb-lumos/bi@0.24.0-next.2': resolution: {integrity: sha512-KGRv2M0EsZw08qIjauew43VBoG8X6IPiPrW7Bn5nnrqWh0i+JE8ZC4fsS6kGmAhUMw3OcTzinU7cQ318CjaC3Q==} engines: {node: '>=12.0.0'} @@ -2120,6 +2225,10 @@ packages: resolution: {integrity: sha512-VuTyXjulQR1fl3RzfObSBRlFfCdzRi13G120MP9OChH7zaLNartWmPycPF1xcv/FfZIcfCT+dGqUFc+vc7qfGw==} engines: {node: '>=12.0.0'} + '@ckb-lumos/codec@0.23.0': + resolution: {integrity: sha512-FwYooXnsFDjlHHnlFnCTB1UbBzV72I0VjkRpeauFk5nQ4+/75xl28ywK3J14M+0aHTnYU9msXUTRDAGqC0CaNQ==} + engines: {node: '>=12.0.0'} + '@ckb-lumos/codec@0.24.0-next.2': resolution: {integrity: sha512-yPrAwJyLJw4jf2GMMcJHRE2Z/I9ZD0e7VzzHA0rwTNaaXHpjZWdR5ffBqHGjNAobIrIlJlv9FVDLZTukO1RohA==} engines: {node: '>=12.0.0'} @@ -2144,6 +2253,10 @@ packages: resolution: {integrity: sha512-C/Vjvbh+GStxA/9vcj6oI1apZQRoydIvc8T1DR5Dh3F9K1q8NUSnJ43bLNOcwusdMWDkRNNS0jyoKirtLJy5Hg==} engines: {node: '>=12.0.0'} + '@ckb-lumos/toolkit@0.23.0': + resolution: {integrity: sha512-7LTsUFfoNCBWJLgh+V/QFnemjGw+y4mmLeQvubwYuJqIPIhIpwKUuKRzkvVG8snA8xVQSfjSSQOs5m3mKp66Kg==} + engines: {node: '>=12.0.0'} + '@ckb-lumos/toolkit@0.24.0-next.2': resolution: {integrity: sha512-faqOZpj0H21vsqfQXfzRRQUEgF3vZ9i3PcqyF7hNbrNeR6VUcIzJL8QskhjFhBusxAvKf56QbX0/T06/PAgbfg==} engines: {node: '>=12.0.0'} @@ -2635,156 +2748,312 @@ packages: cpu: [ppc64] os: [aix] + '@esbuild/aix-ppc64@0.27.2': + resolution: {integrity: sha512-GZMB+a0mOMZs4MpDbj8RJp4cw+w1WV5NYD6xzgvzUJ5Ek2jerwfO2eADyI6ExDSUED+1X8aMbegahsJi+8mgpw==} + engines: {node: '>=18'} + cpu: [ppc64] + os: [aix] + '@esbuild/android-arm64@0.25.9': resolution: {integrity: sha512-IDrddSmpSv51ftWslJMvl3Q2ZT98fUSL2/rlUXuVqRXHCs5EUF1/f+jbjF5+NG9UffUDMCiTyh8iec7u8RlTLg==} engines: {node: '>=18'} cpu: [arm64] os: [android] + '@esbuild/android-arm64@0.27.2': + resolution: {integrity: sha512-pvz8ZZ7ot/RBphf8fv60ljmaoydPU12VuXHImtAs0XhLLw+EXBi2BLe3OYSBslR4rryHvweW5gmkKFwTiFy6KA==} + engines: {node: '>=18'} + cpu: [arm64] + os: [android] + '@esbuild/android-arm@0.25.9': resolution: {integrity: sha512-5WNI1DaMtxQ7t7B6xa572XMXpHAaI/9Hnhk8lcxF4zVN4xstUgTlvuGDorBguKEnZO70qwEcLpfifMLoxiPqHQ==} engines: {node: '>=18'} cpu: [arm] os: [android] + '@esbuild/android-arm@0.27.2': + resolution: {integrity: sha512-DVNI8jlPa7Ujbr1yjU2PfUSRtAUZPG9I1RwW4F4xFB1Imiu2on0ADiI/c3td+KmDtVKNbi+nffGDQMfcIMkwIA==} + engines: {node: '>=18'} + cpu: [arm] + os: [android] + '@esbuild/android-x64@0.25.9': resolution: {integrity: sha512-I853iMZ1hWZdNllhVZKm34f4wErd4lMyeV7BLzEExGEIZYsOzqDWDf+y082izYUE8gtJnYHdeDpN/6tUdwvfiw==} engines: {node: '>=18'} cpu: [x64] os: [android] + '@esbuild/android-x64@0.27.2': + resolution: {integrity: sha512-z8Ank4Byh4TJJOh4wpz8g2vDy75zFL0TlZlkUkEwYXuPSgX8yzep596n6mT7905kA9uHZsf/o2OJZubl2l3M7A==} + engines: {node: '>=18'} + cpu: [x64] + os: [android] + '@esbuild/darwin-arm64@0.25.9': resolution: {integrity: sha512-XIpIDMAjOELi/9PB30vEbVMs3GV1v2zkkPnuyRRURbhqjyzIINwj+nbQATh4H9GxUgH1kFsEyQMxwiLFKUS6Rg==} engines: {node: '>=18'} cpu: [arm64] os: [darwin] + '@esbuild/darwin-arm64@0.27.2': + resolution: {integrity: sha512-davCD2Zc80nzDVRwXTcQP/28fiJbcOwvdolL0sOiOsbwBa72kegmVU0Wrh1MYrbuCL98Omp5dVhQFWRKR2ZAlg==} + engines: {node: '>=18'} + cpu: [arm64] + os: [darwin] + '@esbuild/darwin-x64@0.25.9': resolution: {integrity: sha512-jhHfBzjYTA1IQu8VyrjCX4ApJDnH+ez+IYVEoJHeqJm9VhG9Dh2BYaJritkYK3vMaXrf7Ogr/0MQ8/MeIefsPQ==} engines: {node: '>=18'} cpu: [x64] os: [darwin] + '@esbuild/darwin-x64@0.27.2': + resolution: {integrity: sha512-ZxtijOmlQCBWGwbVmwOF/UCzuGIbUkqB1faQRf5akQmxRJ1ujusWsb3CVfk/9iZKr2L5SMU5wPBi1UWbvL+VQA==} + engines: {node: '>=18'} + cpu: [x64] + os: [darwin] + '@esbuild/freebsd-arm64@0.25.9': resolution: {integrity: sha512-z93DmbnY6fX9+KdD4Ue/H6sYs+bhFQJNCPZsi4XWJoYblUqT06MQUdBCpcSfuiN72AbqeBFu5LVQTjfXDE2A6Q==} engines: {node: '>=18'} cpu: [arm64] os: [freebsd] + '@esbuild/freebsd-arm64@0.27.2': + resolution: {integrity: sha512-lS/9CN+rgqQ9czogxlMcBMGd+l8Q3Nj1MFQwBZJyoEKI50XGxwuzznYdwcav6lpOGv5BqaZXqvBSiB/kJ5op+g==} + engines: {node: '>=18'} + cpu: [arm64] + os: [freebsd] + '@esbuild/freebsd-x64@0.25.9': resolution: {integrity: sha512-mrKX6H/vOyo5v71YfXWJxLVxgy1kyt1MQaD8wZJgJfG4gq4DpQGpgTB74e5yBeQdyMTbgxp0YtNj7NuHN0PoZg==} engines: {node: '>=18'} cpu: [x64] os: [freebsd] + '@esbuild/freebsd-x64@0.27.2': + resolution: {integrity: sha512-tAfqtNYb4YgPnJlEFu4c212HYjQWSO/w/h/lQaBK7RbwGIkBOuNKQI9tqWzx7Wtp7bTPaGC6MJvWI608P3wXYA==} + engines: {node: '>=18'} + cpu: [x64] + os: [freebsd] + '@esbuild/linux-arm64@0.25.9': resolution: {integrity: sha512-BlB7bIcLT3G26urh5Dmse7fiLmLXnRlopw4s8DalgZ8ef79Jj4aUcYbk90g8iCa2467HX8SAIidbL7gsqXHdRw==} engines: {node: '>=18'} cpu: [arm64] os: [linux] + '@esbuild/linux-arm64@0.27.2': + resolution: {integrity: sha512-hYxN8pr66NsCCiRFkHUAsxylNOcAQaxSSkHMMjcpx0si13t1LHFphxJZUiGwojB1a/Hd5OiPIqDdXONia6bhTw==} + engines: {node: '>=18'} + cpu: [arm64] + os: [linux] + '@esbuild/linux-arm@0.25.9': resolution: {integrity: sha512-HBU2Xv78SMgaydBmdor38lg8YDnFKSARg1Q6AT0/y2ezUAKiZvc211RDFHlEZRFNRVhcMamiToo7bDx3VEOYQw==} engines: {node: '>=18'} cpu: [arm] os: [linux] + '@esbuild/linux-arm@0.27.2': + resolution: {integrity: sha512-vWfq4GaIMP9AIe4yj1ZUW18RDhx6EPQKjwe7n8BbIecFtCQG4CfHGaHuh7fdfq+y3LIA2vGS/o9ZBGVxIDi9hw==} + engines: {node: '>=18'} + cpu: [arm] + os: [linux] + '@esbuild/linux-ia32@0.25.9': resolution: {integrity: sha512-e7S3MOJPZGp2QW6AK6+Ly81rC7oOSerQ+P8L0ta4FhVi+/j/v2yZzx5CqqDaWjtPFfYz21Vi1S0auHrap3Ma3A==} engines: {node: '>=18'} cpu: [ia32] os: [linux] + '@esbuild/linux-ia32@0.27.2': + resolution: {integrity: sha512-MJt5BRRSScPDwG2hLelYhAAKh9imjHK5+NE/tvnRLbIqUWa+0E9N4WNMjmp/kXXPHZGqPLxggwVhz7QP8CTR8w==} + engines: {node: '>=18'} + cpu: [ia32] + os: [linux] + '@esbuild/linux-loong64@0.25.9': resolution: {integrity: sha512-Sbe10Bnn0oUAB2AalYztvGcK+o6YFFA/9829PhOCUS9vkJElXGdphz0A3DbMdP8gmKkqPmPcMJmJOrI3VYB1JQ==} engines: {node: '>=18'} cpu: [loong64] os: [linux] + '@esbuild/linux-loong64@0.27.2': + resolution: {integrity: sha512-lugyF1atnAT463aO6KPshVCJK5NgRnU4yb3FUumyVz+cGvZbontBgzeGFO1nF+dPueHD367a2ZXe1NtUkAjOtg==} + engines: {node: '>=18'} + cpu: [loong64] + os: [linux] + '@esbuild/linux-mips64el@0.25.9': resolution: {integrity: sha512-YcM5br0mVyZw2jcQeLIkhWtKPeVfAerES5PvOzaDxVtIyZ2NUBZKNLjC5z3/fUlDgT6w89VsxP2qzNipOaaDyA==} engines: {node: '>=18'} cpu: [mips64el] os: [linux] + '@esbuild/linux-mips64el@0.27.2': + resolution: {integrity: sha512-nlP2I6ArEBewvJ2gjrrkESEZkB5mIoaTswuqNFRv/WYd+ATtUpe9Y09RnJvgvdag7he0OWgEZWhviS1OTOKixw==} + engines: {node: '>=18'} + cpu: [mips64el] + os: [linux] + '@esbuild/linux-ppc64@0.25.9': resolution: {integrity: sha512-++0HQvasdo20JytyDpFvQtNrEsAgNG2CY1CLMwGXfFTKGBGQT3bOeLSYE2l1fYdvML5KUuwn9Z8L1EWe2tzs1w==} engines: {node: '>=18'} cpu: [ppc64] os: [linux] + '@esbuild/linux-ppc64@0.27.2': + resolution: {integrity: sha512-C92gnpey7tUQONqg1n6dKVbx3vphKtTHJaNG2Ok9lGwbZil6DrfyecMsp9CrmXGQJmZ7iiVXvvZH6Ml5hL6XdQ==} + engines: {node: '>=18'} + cpu: [ppc64] + os: [linux] + '@esbuild/linux-riscv64@0.25.9': resolution: {integrity: sha512-uNIBa279Y3fkjV+2cUjx36xkx7eSjb8IvnL01eXUKXez/CBHNRw5ekCGMPM0BcmqBxBcdgUWuUXmVWwm4CH9kg==} engines: {node: '>=18'} cpu: [riscv64] os: [linux] + '@esbuild/linux-riscv64@0.27.2': + resolution: {integrity: sha512-B5BOmojNtUyN8AXlK0QJyvjEZkWwy/FKvakkTDCziX95AowLZKR6aCDhG7LeF7uMCXEJqwa8Bejz5LTPYm8AvA==} + engines: {node: '>=18'} + cpu: [riscv64] + os: [linux] + '@esbuild/linux-s390x@0.25.9': resolution: {integrity: sha512-Mfiphvp3MjC/lctb+7D287Xw1DGzqJPb/J2aHHcHxflUo+8tmN/6d4k6I2yFR7BVo5/g7x2Monq4+Yew0EHRIA==} engines: {node: '>=18'} cpu: [s390x] os: [linux] + '@esbuild/linux-s390x@0.27.2': + resolution: {integrity: sha512-p4bm9+wsPwup5Z8f4EpfN63qNagQ47Ua2znaqGH6bqLlmJ4bx97Y9JdqxgGZ6Y8xVTixUnEkoKSHcpRlDnNr5w==} + engines: {node: '>=18'} + cpu: [s390x] + os: [linux] + '@esbuild/linux-x64@0.25.9': resolution: {integrity: sha512-iSwByxzRe48YVkmpbgoxVzn76BXjlYFXC7NvLYq+b+kDjyyk30J0JY47DIn8z1MO3K0oSl9fZoRmZPQI4Hklzg==} engines: {node: '>=18'} cpu: [x64] os: [linux] + '@esbuild/linux-x64@0.27.2': + resolution: {integrity: sha512-uwp2Tip5aPmH+NRUwTcfLb+W32WXjpFejTIOWZFw/v7/KnpCDKG66u4DLcurQpiYTiYwQ9B7KOeMJvLCu/OvbA==} + engines: {node: '>=18'} + cpu: [x64] + os: [linux] + '@esbuild/netbsd-arm64@0.25.9': resolution: {integrity: sha512-9jNJl6FqaUG+COdQMjSCGW4QiMHH88xWbvZ+kRVblZsWrkXlABuGdFJ1E9L7HK+T0Yqd4akKNa/lO0+jDxQD4Q==} engines: {node: '>=18'} cpu: [arm64] os: [netbsd] + '@esbuild/netbsd-arm64@0.27.2': + resolution: {integrity: sha512-Kj6DiBlwXrPsCRDeRvGAUb/LNrBASrfqAIok+xB0LxK8CHqxZ037viF13ugfsIpePH93mX7xfJp97cyDuTZ3cw==} + engines: {node: '>=18'} + cpu: [arm64] + os: [netbsd] + '@esbuild/netbsd-x64@0.25.9': resolution: {integrity: sha512-RLLdkflmqRG8KanPGOU7Rpg829ZHu8nFy5Pqdi9U01VYtG9Y0zOG6Vr2z4/S+/3zIyOxiK6cCeYNWOFR9QP87g==} engines: {node: '>=18'} cpu: [x64] os: [netbsd] + '@esbuild/netbsd-x64@0.27.2': + resolution: {integrity: sha512-HwGDZ0VLVBY3Y+Nw0JexZy9o/nUAWq9MlV7cahpaXKW6TOzfVno3y3/M8Ga8u8Yr7GldLOov27xiCnqRZf0tCA==} + engines: {node: '>=18'} + cpu: [x64] + os: [netbsd] + '@esbuild/openbsd-arm64@0.25.9': resolution: {integrity: sha512-YaFBlPGeDasft5IIM+CQAhJAqS3St3nJzDEgsgFixcfZeyGPCd6eJBWzke5piZuZ7CtL656eOSYKk4Ls2C0FRQ==} engines: {node: '>=18'} cpu: [arm64] os: [openbsd] + '@esbuild/openbsd-arm64@0.27.2': + resolution: {integrity: sha512-DNIHH2BPQ5551A7oSHD0CKbwIA/Ox7+78/AWkbS5QoRzaqlev2uFayfSxq68EkonB+IKjiuxBFoV8ESJy8bOHA==} + engines: {node: '>=18'} + cpu: [arm64] + os: [openbsd] + '@esbuild/openbsd-x64@0.25.9': resolution: {integrity: sha512-1MkgTCuvMGWuqVtAvkpkXFmtL8XhWy+j4jaSO2wxfJtilVCi0ZE37b8uOdMItIHz4I6z1bWWtEX4CJwcKYLcuA==} engines: {node: '>=18'} cpu: [x64] os: [openbsd] + '@esbuild/openbsd-x64@0.27.2': + resolution: {integrity: sha512-/it7w9Nb7+0KFIzjalNJVR5bOzA9Vay+yIPLVHfIQYG/j+j9VTH84aNB8ExGKPU4AzfaEvN9/V4HV+F+vo8OEg==} + engines: {node: '>=18'} + cpu: [x64] + os: [openbsd] + '@esbuild/openharmony-arm64@0.25.9': resolution: {integrity: sha512-4Xd0xNiMVXKh6Fa7HEJQbrpP3m3DDn43jKxMjxLLRjWnRsfxjORYJlXPO4JNcXtOyfajXorRKY9NkOpTHptErg==} engines: {node: '>=18'} cpu: [arm64] os: [openharmony] + '@esbuild/openharmony-arm64@0.27.2': + resolution: {integrity: sha512-LRBbCmiU51IXfeXk59csuX/aSaToeG7w48nMwA6049Y4J4+VbWALAuXcs+qcD04rHDuSCSRKdmY63sruDS5qag==} + engines: {node: '>=18'} + cpu: [arm64] + os: [openharmony] + '@esbuild/sunos-x64@0.25.9': resolution: {integrity: sha512-WjH4s6hzo00nNezhp3wFIAfmGZ8U7KtrJNlFMRKxiI9mxEK1scOMAaa9i4crUtu+tBr+0IN6JCuAcSBJZfnphw==} engines: {node: '>=18'} cpu: [x64] os: [sunos] + '@esbuild/sunos-x64@0.27.2': + resolution: {integrity: sha512-kMtx1yqJHTmqaqHPAzKCAkDaKsffmXkPHThSfRwZGyuqyIeBvf08KSsYXl+abf5HDAPMJIPnbBfXvP2ZC2TfHg==} + engines: {node: '>=18'} + cpu: [x64] + os: [sunos] + '@esbuild/win32-arm64@0.25.9': resolution: {integrity: sha512-mGFrVJHmZiRqmP8xFOc6b84/7xa5y5YvR1x8djzXpJBSv/UsNK6aqec+6JDjConTgvvQefdGhFDAs2DLAds6gQ==} engines: {node: '>=18'} cpu: [arm64] os: [win32] + '@esbuild/win32-arm64@0.27.2': + resolution: {integrity: sha512-Yaf78O/B3Kkh+nKABUF++bvJv5Ijoy9AN1ww904rOXZFLWVc5OLOfL56W+C8F9xn5JQZa3UX6m+IktJnIb1Jjg==} + engines: {node: '>=18'} + cpu: [arm64] + os: [win32] + '@esbuild/win32-ia32@0.25.9': resolution: {integrity: sha512-b33gLVU2k11nVx1OhX3C8QQP6UHQK4ZtN56oFWvVXvz2VkDoe6fbG8TOgHFxEvqeqohmRnIHe5A1+HADk4OQww==} engines: {node: '>=18'} cpu: [ia32] os: [win32] + '@esbuild/win32-ia32@0.27.2': + resolution: {integrity: sha512-Iuws0kxo4yusk7sw70Xa2E2imZU5HoixzxfGCdxwBdhiDgt9vX9VUCBhqcwY7/uh//78A1hMkkROMJq9l27oLQ==} + engines: {node: '>=18'} + cpu: [ia32] + os: [win32] + '@esbuild/win32-x64@0.25.9': resolution: {integrity: sha512-PPOl1mi6lpLNQxnGoyAfschAodRFYXJ+9fs6WHXz7CSWKbOqiMZsubC+BQsVKuul+3vKLuwTHsS2c2y9EoKwxQ==} engines: {node: '>=18'} cpu: [x64] os: [win32] + '@esbuild/win32-x64@0.27.2': + resolution: {integrity: sha512-sRdU18mcKf7F+YgheI/zGf5alZatMUTKj/jNS6l744f9u3WFu4v7twcUI9vu4mknF4Y9aDlblIie0IM+5xxaqQ==} + engines: {node: '>=18'} + cpu: [x64] + os: [win32] + '@eslint-community/eslint-utils@4.7.0': resolution: {integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} @@ -2834,6 +3103,11 @@ packages: '@euberdeveloper/eslint-plugin@2.7.0': resolution: {integrity: sha512-IyZfysHjYCSU6Ty86imkCZmZ5diTAOKn7DlEmEO1yHhFjvVk+xFr0ApjTD7TyIQolnBPixZNw477V7mq86llcw==} + '@exact-realty/multipart-parser@1.0.14': + resolution: {integrity: sha512-ln1+s1XOvRY9NRof3lpjWJZfSoV5XOWdVgK7sYeE3TAt0brtB+pIPJpSbxaol/490re2rcMEo24VZXeffKm8Aw==} + engines: {node: '>=16.0.0', npm: '>=8.0.0'} + deprecated: Package has moved to @apeleghq/multipart-parser + '@floating-ui/core@1.7.3': resolution: {integrity: sha512-sGnvb5dmrJaKEZ+LDIpguvdX3bDlEllmv4/ClQ9awcmCZrlx5jQyyMWFM5kBI+EyNOCDDiKk8il0zeuX3Zlg/w==} @@ -3205,10 +3479,23 @@ packages: resolution: {integrity: sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==} engines: {node: '>=8'} + '@jest/console@29.7.0': + resolution: {integrity: sha512-5Ni4CU7XHQi32IJ398EEP4RrB8eV09sXP2ROqD4bksHrnTree52PsxvX8tpL8LvTZ3pFzXyPbNQReSN41CAhOg==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/console@30.1.1': resolution: {integrity: sha512-f7TGqR1k4GtN5pyFrKmq+ZVndesiwLU33yDpJIGMS9aW+j6hKjue7ljeAdznBsH9kAnxUWe2Y+Y3fLV/FJt3gA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/core@29.7.0': + resolution: {integrity: sha512-n7aeXWKMnGtDA48y8TLWJPJmLmmZ642Ceo78cYWEpiD7FzDgmNDV/GCVRorPABdXLJZ/9wzzgZAlHjXjxDHGsg==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + peerDependencies: + node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 + peerDependenciesMeta: + node-notifier: + optional: true + '@jest/core@30.1.1': resolution: {integrity: sha512-3ncU9peZ3D2VdgRkdZtUceTrDgX5yiDRwAFjtxNfU22IiZrpVWlv/FogzDLYSJQptQGfFo3PcHK86a2oG6WUGg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -3222,18 +3509,34 @@ packages: resolution: {integrity: sha512-n5H8QLDJ47QqbCNn5SuFjCRDrOLEZ0h8vAHCK5RL9Ls7Xa8AQLa/YxAc9UjFqoEDM48muwtBGjtMY5cr0PLDCw==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/environment@29.7.0': + resolution: {integrity: sha512-aQIfHDq33ExsN4jP1NWGXhxgQ/wixs60gDiKO+XVMd8Mn0NWPWgc34ZQDTb2jKaUWQ7MuwoitXAsN2XVXNMpAw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/environment@30.1.1': resolution: {integrity: sha512-yWHbU+3j7ehQE+NRpnxRvHvpUhoohIjMePBbIr8lfe0cWVb0WeTf80DNux1GPJa18CDHiIU5DtksGUfxcDE+Rw==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/expect-utils@29.7.0': + resolution: {integrity: sha512-GlsNBWiFQFCVi9QVSx7f5AgMeLxe9YCCs5PuP2O2LdjDAA8Jh9eX7lA1Jq/xdXw3Wb3hyvlFNfZIfcRetSzYcA==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/expect-utils@30.1.1': resolution: {integrity: sha512-5YUHr27fpJ64dnvtu+tt11ewATynrHkGYD+uSFgRr8V2eFJis/vEXgToyLwccIwqBihVfz9jwio+Zr1ab1Zihw==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/expect@29.7.0': + resolution: {integrity: sha512-8uMeAMycttpva3P1lBHB8VciS9V0XAr3GymPpipdyQXbBcuhkLQOSe8E/p92RyAdToS6ZD1tFkX+CkhoECE0dQ==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/expect@30.1.1': resolution: {integrity: sha512-3vHIHsF+qd3D8FU2c7U5l3rg1fhDwAYcGyHyZAi94YIlTwcJ+boNhRyJf373cl4wxbOX+0Q7dF40RTrTFTSuig==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/fake-timers@29.7.0': + resolution: {integrity: sha512-q4DH1Ha4TTFPdxLsqDXK1d3+ioSL7yL5oCMJZgDYm6i+6CygW5E5xVr/D1HdsGxjt1ZWSfUAs9OxSB/BNelWrQ==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/fake-timers@30.1.1': resolution: {integrity: sha512-fK/25dNgBNYPw3eLi2CRs57g1H04qBAFNMsUY3IRzkfx/m4THe0E1zF+yGQBOMKKc2XQVdc9EYbJ4hEm7/2UtA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -3242,6 +3545,10 @@ packages: resolution: {integrity: sha512-eMbZE2hUnx1WV0pmURZY9XoXPkUYjpc55mb0CrhtdWLtzMQPFvu/rZkTLZFTsdaVQa+Tr4eWAteqcUzoawq/uA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/globals@29.7.0': + resolution: {integrity: sha512-mpiz3dutLbkW2MNFubUGUEVLkTGiqW6yLVTA+JbP6fI6J5iL9Y0Nlg8k95pcF8ctKwCS7WVxteBs29hhfAotzQ==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/globals@30.1.1': resolution: {integrity: sha512-NNUUkHT2TU/xztZl6r1UXvJL+zvCwmZsQDmK69fVHHcB9fBtlu3FInnzOve/ZoyKnWY8JXWJNT+Lkmu1+ubXUA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -3250,6 +3557,15 @@ packages: resolution: {integrity: sha512-gWp7NfQW27LaBQz3TITS8L7ZCQ0TLvtmI//4OwlQRx4rnWxcPNIYjxZpDcN4+UlGxgm3jS5QPz8IPTCkb59wZA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/reporters@29.7.0': + resolution: {integrity: sha512-DApq0KJbJOEzAFYjHADNNxAE3KbhxQB1y5Kplb5Waqw6zVbuWatSnMjE5gs8FUgEPmNsnZA3NCWl9NG0ia04Pg==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + peerDependencies: + node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 + peerDependenciesMeta: + node-notifier: + optional: true + '@jest/reporters@30.1.1': resolution: {integrity: sha512-Hb2Bq80kahOC6Sv2waEaH1rEU6VdFcM6WHaRBWQF9tf30+nJHxhl/Upbgo9+25f0mOgbphxvbwSMjSgy9gW/FA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -3271,18 +3587,34 @@ packages: resolution: {integrity: sha512-TkVBc9wuN22TT8hESRFmjjg/xIMu7z0J3UDYtIRydzCqlLPTB7jK1DDBKdnTUZ4zL3z3rnPpzV6rL1Uzh87sXg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/source-map@29.6.3': + resolution: {integrity: sha512-MHjT95QuipcPrpLM+8JMSzFx6eHp5Bm+4XeFDJlwsvVBjmKNiIAvasGK2fxz2WbGRlnvqehFbh07MMa7n3YJnw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/source-map@30.0.1': resolution: {integrity: sha512-MIRWMUUR3sdbP36oyNyhbThLHyJ2eEDClPCiHVbrYAe5g3CHRArIVpBw7cdSB5fr+ofSfIb2Tnsw8iEHL0PYQg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/test-result@29.7.0': + resolution: {integrity: sha512-Fdx+tv6x1zlkJPcWXmMDAG2HBnaR9XPSd5aDWQVsfrZmLVT3lU1cwyxLgRmXR9yrq4NBoEm9BMsfgFzTQAbJYA==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/test-result@30.1.1': resolution: {integrity: sha512-bMdj7fNu8iZuBPSnbVir5ezvWmVo4jrw7xDE+A33Yb3ENCoiJK9XgOLgal+rJ9XSKjsL7aPUMIo87zhN7I5o2w==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/test-sequencer@29.7.0': + resolution: {integrity: sha512-GQwJ5WZVrKnOJuiYiAF52UNUJXgTZx1NHjFSEB0qEMmSZKAkdMoIzw/Cj6x6NF4AvV23AUqDpFzQkN/eYCYTxw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/test-sequencer@30.1.1': resolution: {integrity: sha512-yruRdLXSA3HYD/MTNykgJ6VYEacNcXDFRMqKVAwlYegmxICUiT/B++CNuhJnYJzKYks61iYnjVsMwbUqmmAYJg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + '@jest/transform@29.7.0': + resolution: {integrity: sha512-ok/BTPFzFKVMwO5eOHRrvnBVHdRy9IrsrW1GpMaQ9MCnilNLXQKmAX8s1YXDFaai9xJpac2ySzV0YeRRECr2Vw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + '@jest/transform@30.1.1': resolution: {integrity: sha512-PHIA2AbAASBfk6evkNifvmx9lkOSkmvaQoO6VSpuL8+kQqDMHeDoJ7RU3YP1wWAMD7AyQn9UL5iheuFYCC4lqQ==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -3585,6 +3917,9 @@ packages: resolution: {integrity: sha512-h8VUBlE8R42+XIDO229cgisD287im3kdY6nbNZJFjc6ZvKIXPYXe6Vc/t+kyjFdMFyt5JpapzTsEg8n63w5/lw==} engines: {node: '>= 20.19.0'} + '@noble/secp256k1@1.7.2': + resolution: {integrity: sha512-/qzwYl5eFLH8OWIecQWM31qld2g1NfjgylK+TNhqtaUKP37Nm+Y+z30Fjhw0Ct8p9yCQEm2N3W/AckdIb3SMcQ==} + '@nodelib/fs.scandir@2.1.5': resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==} engines: {node: '>= 8'} @@ -3772,6 +4107,9 @@ packages: '@rtsao/scc@1.1.0': resolution: {integrity: sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==} + '@scure/base@1.2.6': + resolution: {integrity: sha512-g/nm5FgUa//MCj1gV09zTJTaM6KBAHqLN907YVQqf7zC49+DcO4B1so4ZX07Ef10Twr6nuqYEH9GEggFXA4Fmg==} + '@scure/base@2.0.0': resolution: {integrity: sha512-3E1kpuZginKkek01ovG8krQ0Z44E3DHPjc5S2rjJw9lZn3KSQOs8S7wqikF/AH7iRanHypj85uGyxk0XAyC37w==} @@ -3836,6 +4174,9 @@ packages: '@sinonjs/commons@3.0.1': resolution: {integrity: sha512-K3mCHKQ9sVh8o1C9cxkwxaOmXoAMlDxC1mYyHrjqOWEcBjYr76t96zL2zlj5dUGZ3HSw240X1qgH3Mjf1yJWpQ==} + '@sinonjs/fake-timers@10.3.0': + resolution: {integrity: sha512-V4BG07kuYSUkTCSBHG8G8TNhM+F19jXFWnQtzj+we8DrkpSBCee9Z3Ms8yiGer/dlmhe35/Xdgyo3/0rQKg7YA==} + '@sinonjs/fake-timers@13.0.5': resolution: {integrity: sha512-36/hTbH2uaWuGVERyC6da9YwGWnzUZXuPro/F2LfsdOsLnCojz/iSH8MxUt/FD2S5XBSVPhmArFUXcpCQ2Hkiw==} @@ -4125,6 +4466,9 @@ packages: '@types/express@5.0.3': resolution: {integrity: sha512-wGA0NX93b19/dZC1J18tKWVIYWyyF2ZjT9vin/NRu0qzzvfVzWjs04iq2rQ3H65vCTQYlRqs3YHfY7zjdV+9Kw==} + '@types/graceful-fs@4.1.9': + resolution: {integrity: sha512-olP3sd1qOEe5dXTSaFvQG+02VdRXcdytWLAZsAq1PecU8uqQAhkrnbli7DagjtXKW/Bl7YJbUsa8MPcuc8LHEQ==} + '@types/gtag.js@0.0.12': resolution: {integrity: sha512-YQV9bUsemkzG81Ea295/nF/5GijnD2Af7QhEofh7xu+kvCN6RdodgNwwGWXB5GMI3NoyvQo0odNctoH/qLMIpg==} @@ -4155,6 +4499,9 @@ packages: '@types/istanbul-reports@3.0.4': resolution: {integrity: sha512-pk2B1NWalF9toCRu6gjBzR69syFjP4Od8WRAX+0mmf9lAjCRicLOWc+ZrxZHx/0XRjotgkF9t6iaMJ+aXcOdZQ==} + '@types/jest@29.5.14': + resolution: {integrity: sha512-ZN+4sdnLUbo8EVvVc2ao0GFW6oVrQRPn4K2lglySj7APvSrgzxHiNNK99us4WDMi57xxA2yggblIAMNhXOotLQ==} + '@types/jest@30.0.0': resolution: {integrity: sha512-XTYugzhuwqWjws0CVz8QpM36+T+Dz5mTEBKhNs/esGLnCIlGdRy+Dq78NRjd7ls7r8BC8ZRMOrKlkO1hU0JOwA==} @@ -4197,6 +4544,9 @@ packages: '@types/node@17.0.45': resolution: {integrity: sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw==} + '@types/node@22.19.3': + resolution: {integrity: sha512-1N9SBnWYOJTrNZCdh/yJE+t910Y128BoyY+zBLWhL3r0TYzlTmFdXrPwHL9DyFZmlEXNQQolTZh3KHV31QDhyA==} + '@types/node@22.7.5': resolution: {integrity: sha512-jML7s2NAzMWc//QSJ1a3prpk78cOPchGvXJsC3C6R6PSMoooztvRVQEz89gmBTBY1SPMaqo5teB4uNHPdetShQ==} @@ -4907,6 +5257,12 @@ packages: b4a@1.6.7: resolution: {integrity: sha512-OnAYlL5b7LEkALw87fUVafQw5rVR9RjwGd4KUwNQ6DrrNmaVaUCgLipfVlzrPQ4tWOR9P0IXGNOx50jYCCdSJg==} + babel-jest@29.7.0: + resolution: {integrity: sha512-BrvGY3xZSwEcCzKvKsCi2GgHqDqsYkOP4/by5xCgIwGXQxIEh+8ew3gmrE1y7XRR6LHZIj6yLYnUi/mm2KXKBg==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + peerDependencies: + '@babel/core': ^7.8.0 + babel-jest@30.1.1: resolution: {integrity: sha512-1bZfC/V03qBCzASvZpNFhx3Ouj6LgOd4KFJm4br/fYOS+tSSvVCE61QmcAVbMTwq/GoB7KN4pzGMoyr9cMxSvQ==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -4923,10 +5279,18 @@ packages: babel-plugin-dynamic-import-node@2.3.3: resolution: {integrity: sha512-jZVI+s9Zg3IqA/kdi0i6UDCybUI3aSBLnglhYbSSjKlV7yF1F/5LWv8MakQmvYpnbJDS6fcBL2KzHSxNCMtWSQ==} + babel-plugin-istanbul@6.1.1: + resolution: {integrity: sha512-Y1IQok9821cC9onCx5otgFfRm7Lm+I+wwxOx738M/WLPZ9Q42m4IG5W0FNX8WLL2gYMZo3JkuXIH2DOpWM+qwA==} + engines: {node: '>=8'} + babel-plugin-istanbul@7.0.0: resolution: {integrity: sha512-C5OzENSx/A+gt7t4VH1I2XsflxyPUmXRFPKBxt33xncdOmq7oROVM3bZv9Ysjjkv8OJYDMa+tKuKMvqU/H3xdw==} engines: {node: '>=12'} + babel-plugin-jest-hoist@29.6.3: + resolution: {integrity: sha512-ESAc/RJvGTFEzRwOTT4+lNDk/GNHMkKbNzsvT0qKRfDyyYTskxB5rnU2njIDYVxXCBHHEI1c0YwHob3WaYujOg==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + babel-plugin-jest-hoist@30.0.1: resolution: {integrity: sha512-zTPME3pI50NsFW8ZBaVIOeAxzEY7XHlmWeXXu9srI+9kNfzCUTy8MFan46xOGZY8NZThMqq+e3qZUKsvXbasnQ==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -4951,6 +5315,12 @@ packages: peerDependencies: '@babel/core': ^7.0.0 || ^8.0.0-0 + babel-preset-jest@29.6.3: + resolution: {integrity: sha512-0B3bhxR6snWXJZtR/RliHTDPRgn1sNHOR0yVtq/IiQFyuOVjFS+wuio/R4gSNkyYmKmJB4wGZv2NZanmKmTnNA==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + peerDependencies: + '@babel/core': ^7.0.0 + babel-preset-jest@30.0.1: resolution: {integrity: sha512-+YHejD5iTWI46cZmcc/YtX4gaKBtdqCHCVfuVinizVpbmyjO3zYmeuyFdfA8duRqQZfgCAMlsfmkVbJ+e2MAJw==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -4963,6 +5333,9 @@ packages: balanced-match@1.0.2: resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} + base-x@3.0.11: + resolution: {integrity: sha512-xz7wQ8xDhdyP7tQxwdteLYeFfS68tSMNCZ/Y37WJ4bhGfKPpqEIlmIyueQHqOyoPhE6xNUqjzRr8ra0eF9VRvA==} + base-x@4.0.1: resolution: {integrity: sha512-uAZ8x6r6S3aUM9rbHGVOIsR15U/ZSc82b3ymnCPsT45Gk1DDvhDPdIgB5MrhirZWt+5K0EEPQH985kNqZgNPFw==} @@ -4993,6 +5366,18 @@ packages: resolution: {integrity: sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==} engines: {node: '>=8'} + bip174@2.1.1: + resolution: {integrity: sha512-mdFV5+/v0XyNYXjBS6CQPLo9ekCx4gtKZFnJm5PMto7Fs9hTTDpkkzOB7/FtluRI6JbUUAu+snTYfJRgHLZbZQ==} + engines: {node: '>=8.0.0'} + + bip32@4.0.0: + resolution: {integrity: sha512-aOGy88DDlVUhspIXJN+dVEtclhIsfAUppD43V0j40cPTld3pv/0X/MlrZSZ6jowIaQQzFwP8M6rFU2z2mVYjDQ==} + engines: {node: '>=6.0.0'} + + bitcoinjs-lib@6.1.6: + resolution: {integrity: sha512-Fk8+Vc+e2rMoDU5gXkW9tD+313rhkm5h6N9HfZxXvYU9LedttVvmXKTgd9k5rsQJjkSfsv6XRM8uhJv94SrvcA==} + engines: {node: '>=8.0.0'} + bl@4.1.0: resolution: {integrity: sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==} @@ -5049,12 +5434,21 @@ packages: resolution: {integrity: sha512-pd8DCoxmbgc7hyPKOvxtqNcjYoOsABPQdcCUjGp3d42VR2CX1ORhk2A87oqqu5R1kk+76nsxZupkmyd+MVtCog==} engines: {node: '>= 6'} + bs58@4.0.1: + resolution: {integrity: sha512-Ok3Wdf5vOIlBrgCvTq96gBkJw+JUEzdBgyaza5HLtPm7yTHkjRy8+JzNyHF7BHa0bNWOQIp3m5YF0nnFcOIKLw==} + bs58@5.0.0: resolution: {integrity: sha512-r+ihvQJvahgYT50JD05dyJNKlmmSlMoOGwn1lCcEzanPglg7TxYjioQUYehQ9mAR/+hOSd2jRc/Z2y5UxBymvQ==} bs58@6.0.0: resolution: {integrity: sha512-PD0wEnEYg6ijszw/u8s+iI3H17cTymlrwkKhDhPZq+Sokl3AU4htyBFTjAeNAlCCmg0f53g6ih3jATyCKftTfw==} + bs58check@2.1.2: + resolution: {integrity: sha512-0TS1jicxdU09dwJMNZtVAfzPi6Q6QeN0pM1Fkzrjn+XYHvzMKPU3pHVpva+769iNVSfIYWf7LJ6WR+BuuMf8cA==} + + bs58check@3.0.1: + resolution: {integrity: sha512-hjuuJvoWEybo7Hn/0xOrczQKKEKD63WguEjlhLExYs2wUBcebDC1jDNK17eEAD2lYfw82d5ASC1d7K3SWszjaQ==} + bs58check@4.0.0: resolution: {integrity: sha512-FsGDOnFg9aVI9erdriULkd/JjEWONV/lQE5aYziB5PoBsXRind56lh8doIZIc9X4HoxT5x4bLjMWN1/NB8Zp5g==} @@ -5215,6 +5609,13 @@ packages: resolution: {integrity: sha512-l+2bNRMiQgcfILUi33labAZYIWlH1kWDp+ecNo5iisRKrbm0xcRyCww71/YU0Fkw0mAFpz9bJayXPjey6vkmaQ==} engines: {node: '>=8'} + cipher-base@1.0.7: + resolution: {integrity: sha512-Mz9QMT5fJe7bKI7MH31UilT5cEK5EHHRCccw/YRFsRY47AuNgaV6HY3rscp0/I4Q+tTW/5zoqpSeRRI54TkDWA==} + engines: {node: '>= 0.10'} + + cjs-module-lexer@1.4.3: + resolution: {integrity: sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==} + cjs-module-lexer@2.1.0: resolution: {integrity: sha512-UX0OwmYRYQQetfrLEZeewIFFI+wSTofC+pMBLNuH3RUuu/xzG1oz84UCEDOSoQlN3fZ4+AzmV50ZYvGqkMh9yA==} @@ -5453,6 +5854,14 @@ packages: typescript: optional: true + create-hash@1.2.0: + resolution: {integrity: sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg==} + + create-jest@29.7.0: + resolution: {integrity: sha512-Adz2bdH0Vq3F53KEMJOoftQFutWCukm6J24wbPWRO4k1kMY7gS7ds/uoJkNuV8wDCtWWnuwGcJwpWcih+zEW1Q==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + hasBin: true + create-require@1.1.1: resolution: {integrity: sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==} @@ -5765,6 +6174,10 @@ packages: dezalgo@1.0.4: resolution: {integrity: sha512-rXSP0bf+5n0Qonsb+SVVfNfIsimO4HEtmnIpPHY8Q1UCzKlQrDMfdobr8nJOOsRgWCyMRqeSBQzmWUMq7zvVig==} + diff-sequences@29.6.3: + resolution: {integrity: sha512-EjePK1srD3P08o2j4f0ExnylqRs5B9tJjcp9t1krH2qRi8CCdsYfwe9JgSLurFBWwq4uOlipzfk5fHNvwFKr8Q==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + diff@4.0.2: resolution: {integrity: sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==} engines: {node: '>=0.3.1'} @@ -5844,6 +6257,10 @@ packages: eastasianwidth@0.2.0: resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==} + ecpair@2.1.0: + resolution: {integrity: sha512-cL/mh3MtJutFOvFc27GPZE2pWL3a3k4YvzUWEOvilnfZVlH3Jwgx/7d6tlD7/75tNk8TG2m+7Kgtz0SI1tWcqw==} + engines: {node: '>=8.0.0'} + ee-first@1.1.1: resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} @@ -5952,6 +6369,11 @@ packages: engines: {node: '>=18'} hasBin: true + esbuild@0.27.2: + resolution: {integrity: sha512-HyNQImnsOC7X9PMNaCIeAm4ISCQXs5a5YasTXVliKv4uuBo1dKrG0A+uQS8M5eXjVMnLg3WgXaKvprHlFJQffw==} + engines: {node: '>=18'} + hasBin: true + escalade@3.2.0: resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==} engines: {node: '>=6'} @@ -6236,10 +6658,18 @@ packages: resolution: {integrity: sha512-+I6B/IkJc1o/2tiURyz/ivu/O0nKNEArIUB5O7zBrlDVJr22SCLH3xTeEry428LvFhRzIA1g8izguxJ/gbNcVQ==} engines: {node: '>= 0.8.0'} + exit@0.1.2: + resolution: {integrity: sha512-Zk/eNKV2zbjpKzrsQ+n1G6poVbErQxJ0LBOJXaKZ1EViLzH+hrLu9cdXI4zw9dBQJslwBEpbQ2P1oS7nDxs6jQ==} + engines: {node: '>= 0.8.0'} + expect-type@1.2.2: resolution: {integrity: sha512-JhFGDVJ7tmDJItKhYgJCGLOWjuK9vPxiXoUFLwLDc99NlmklilbiQJwoctZtt13+xMw91MCk/REan6MWHqDjyA==} engines: {node: '>=12.0.0'} + expect@29.7.0: + resolution: {integrity: sha512-2Zks0hf1VLFYI1kbh0I5jP3KHHyCHpkfyHBzsSXRFgl/Bg9mWYfMW8oD+PdMPlEwy5HNsR9JutYy6pMeOh61nw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + expect@30.1.1: resolution: {integrity: sha512-OKe7cdic4qbfWd/CcgwJvvCrNX2KWfuMZee9AfJHL1gTYmvqjBjZG1a2NwfhspBzxzlXwsN75WWpKTYfsJpBxg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -6644,6 +7074,10 @@ packages: resolution: {integrity: sha512-IrsVwUHhEULx3R8f/aA8AHuEzAorplsab/v8HBzEiIukwq5i/EC+xmOW+HfP1OaDP+2JkgT1yILHN2O3UFIbcA==} engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} + hash-base@3.1.2: + resolution: {integrity: sha512-Bb33KbowVTIj5s7Ked1OsqHUeCpz//tPwR+E2zJgJKo9Z5XolZ9b6bdUgjmYlwnWhoOQKoTd1TYToZGn5mAYOg==} + engines: {node: '>= 0.8'} + hash.js@1.1.7: resolution: {integrity: sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==} @@ -7147,6 +7581,10 @@ packages: resolution: {integrity: sha512-O8dpsF+r0WV/8MNRKfnmrtCWhuKjxrq2w+jpzBL5UZKTi2LeVWnWOmWRxFlesJONmc+wLAGvKQZEOanko0LFTg==} engines: {node: '>=8'} + istanbul-lib-instrument@5.2.1: + resolution: {integrity: sha512-pzqtp31nLv/XFOzXGuvhCb8qhjmTVo5vjVk19XE4CRlSWz0KoeJ3bw9XsA7nOp9YBf4qHjwBxkDzKcME/J29Yg==} + engines: {node: '>=8'} + istanbul-lib-instrument@6.0.3: resolution: {integrity: sha512-Vtgk7L/R2JHyyGW07spoFlB8/lpjiOLTjMdms6AFMraYt3BaJauod/NGrfnVG/y4Ix1JEuMRPDPEj2ua+zz1/Q==} engines: {node: '>=10'} @@ -7155,6 +7593,10 @@ packages: resolution: {integrity: sha512-GCfE1mtsHGOELCU8e/Z7YWzpmybrx/+dSTfLrvY8qRmaY6zXTKWn6WQIjaAFw069icm6GVMNkgu0NzI4iPZUNw==} engines: {node: '>=10'} + istanbul-lib-source-maps@4.0.1: + resolution: {integrity: sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw==} + engines: {node: '>=10'} + istanbul-lib-source-maps@5.0.6: resolution: {integrity: sha512-yg2d+Em4KizZC5niWhQaIomgf5WlL4vOOjZ5xGCmF8SnPE/mDWWXgvRExdcpCgh9lLRRa1/fSYp2ymmbJ1pI+A==} engines: {node: '>=10'} @@ -7178,17 +7620,25 @@ packages: resolution: {integrity: sha512-zptv57P3GpL+O0I7VdMJNBZCu+BPHVQUk55Ft8/QCJjTVxrnJHuVuX/0Bl2A6/+2oyR/ZMEuFKwmzqqZ/U5nPQ==} engines: {node: 20 || >=22} + jest-changed-files@29.7.0: + resolution: {integrity: sha512-fEArFiwf1BpQ+4bXSprcDc3/x4HSzL4al2tozwVpDFpsxALjLYdyiIK4e5Vz66GQJIbXJ82+35PtysofptNX2w==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-changed-files@30.0.5: resolution: {integrity: sha512-bGl2Ntdx0eAwXuGpdLdVYVr5YQHnSZlQ0y9HVDu565lCUAe9sj6JOtBbMmBBikGIegne9piDDIOeiLVoqTkz4A==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-circus@29.7.0: + resolution: {integrity: sha512-3E1nCMgipcTkCocFwM90XXQab9bS+GMsjdpmPrlelaxwD93Ad8iVEjX/vvHPdLPnFf+L40u+5+iutRdA1N9myw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-circus@30.1.1: resolution: {integrity: sha512-M3Vd4x5wD7eSJspuTvRF55AkOOBndRxgW3gqQBDlFvbH3X+ASdi8jc+EqXEeAFd/UHulVYIlC4XKJABOhLw6UA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} - jest-cli@30.1.1: - resolution: {integrity: sha512-xm9llxuh5OoI5KZaYzlMhklryHBwg9LZy/gEaaMlXlxb+cZekGNzukU0iblbDo3XOBuN6N0CgK4ykgNRYSEb6g==} - engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-cli@29.7.0: + resolution: {integrity: sha512-OVVobw2IubN/GSYsxETi+gOe7Ka59EFMR/twOU3Jb2GnKKeMGJB5SGUUrEz3SFVmJASUdZUzy83sLNNQ2gZslg==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} hasBin: true peerDependencies: node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 @@ -7196,6 +7646,28 @@ packages: node-notifier: optional: true + jest-cli@30.1.1: + resolution: {integrity: sha512-xm9llxuh5OoI5KZaYzlMhklryHBwg9LZy/gEaaMlXlxb+cZekGNzukU0iblbDo3XOBuN6N0CgK4ykgNRYSEb6g==} + engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + hasBin: true + peerDependencies: + node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 + peerDependenciesMeta: + node-notifier: + optional: true + + jest-config@29.7.0: + resolution: {integrity: sha512-uXbpfeQ7R6TZBqI3/TxCU4q4ttk3u0PJeC+E0zbfSoSjq6bJ7buBPxzQPL0ifrkY4DNu4JUdk0ImlBUYi840eQ==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + peerDependencies: + '@types/node': '*' + ts-node: '>=9.0.0' + peerDependenciesMeta: + '@types/node': + optional: true + ts-node: + optional: true + jest-config@30.1.1: resolution: {integrity: sha512-xuPGUGDw+9fPPnGmddnLnHS/mhKUiJOW7K65vErYmglEPKq65NKwSRchkQ7iv6gqjs2l+YNEsAtbsplxozdOWg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -7211,38 +7683,78 @@ packages: ts-node: optional: true + jest-diff@29.7.0: + resolution: {integrity: sha512-LMIgiIrhigmPrs03JHpxUh2yISK3vLFPkAodPeo0+BuF7wA2FoQbkEg1u8gBYBThncu7e1oEDUfIXVuTqLRUjw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-diff@30.1.1: resolution: {integrity: sha512-LUU2Gx8EhYxpdzTR6BmjL1ifgOAQJQELTHOiPv9KITaKjZvJ9Jmgigx01tuZ49id37LorpGc9dPBPlXTboXScw==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-docblock@29.7.0: + resolution: {integrity: sha512-q617Auw3A612guyaFgsbFeYpNP5t2aoUNLwBUbc/0kD1R4t9ixDbyFTHd1nok4epoVFpr7PmeWHrhvuV3XaJ4g==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-docblock@30.0.1: resolution: {integrity: sha512-/vF78qn3DYphAaIc3jy4gA7XSAz167n9Bm/wn/1XhTLW7tTBIzXtCJpb/vcmc73NIIeeohCbdL94JasyXUZsGA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-each@29.7.0: + resolution: {integrity: sha512-gns+Er14+ZrEoC5fhOfYCY1LOHHr0TI+rQUHZS8Ttw2l7gl+80eHc/gFf2Ktkw0+SIACDTeWvpFcv3B04VembQ==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-each@30.1.0: resolution: {integrity: sha512-A+9FKzxPluqogNahpCv04UJvcZ9B3HamqpDNWNKDjtxVRYB8xbZLFuCr8JAJFpNp83CA0anGQFlpQna9Me+/tQ==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-environment-node@29.7.0: + resolution: {integrity: sha512-DOSwCRqXirTOyheM+4d5YZOrWcdu0LNZ87ewUoywbcb2XR4wKgqiG8vNeYwhjFMbEkfju7wx2GYH0P2gevGvFw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-environment-node@30.1.1: resolution: {integrity: sha512-IaMoaA6saxnJimqCppUDqKck+LKM0Jg+OxyMUIvs1yGd2neiC22o8zXo90k04+tO+49OmgMR4jTgM5e4B0S62Q==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-get-type@29.6.3: + resolution: {integrity: sha512-zrteXnqYxfQh7l5FHyL38jL39di8H8rHoecLH3JNxH3BwOrBsNeabdap5e0I23lD4HHI8W5VFBZqG4Eaq5LNcw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + + jest-haste-map@29.7.0: + resolution: {integrity: sha512-fP8u2pyfqx0K1rGn1R9pyE0/KTn+G7PxktWidOBTqFPLYX0b9ksaMFkhK5vrS3DVun09pckLdlx90QthlW7AmA==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-haste-map@30.1.0: resolution: {integrity: sha512-JLeM84kNjpRkggcGpQLsV7B8W4LNUWz7oDNVnY1Vjj22b5/fAb3kk3htiD+4Na8bmJmjJR7rBtS2Rmq/NEcADg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-leak-detector@29.7.0: + resolution: {integrity: sha512-kYA8IJcSYtST2BY9I+SMC32nDpBT3J2NvWJx8+JCuCdl/CR1I4EKUJROiP8XtCcxqgTTBGJNdbB1A8XRKbTetw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-leak-detector@30.1.0: resolution: {integrity: sha512-AoFvJzwxK+4KohH60vRuHaqXfWmeBATFZpzpmzNmYTtmRMiyGPVhkXpBqxUQunw+dQB48bDf4NpUs6ivVbRv1g==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-matcher-utils@29.7.0: + resolution: {integrity: sha512-sBkD+Xi9DtcChsI3L3u0+N0opgPYnCRPtGcQYrgXmR+hmt/fYfWAL0xRXYU8eWOdfuLgBe0YCW3AFtnRLagq/g==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-matcher-utils@30.1.1: resolution: {integrity: sha512-SuH2QVemK48BNTqReti6FtjsMPFsSOD/ZzRxU1TttR7RiRsRSe78d03bb4Cx6D4bQC/80Q8U4VnaaAH9FlbZ9w==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-message-util@29.7.0: + resolution: {integrity: sha512-GBEV4GRADeP+qtB2+6u61stea8mGcOT4mCtrYISZwfu9/ISHFJ/5zOMXYbpBE9RsS5+Gb63DW4FgmnKJ79Kf6w==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-message-util@30.1.0: resolution: {integrity: sha512-HizKDGG98cYkWmaLUHChq4iN+oCENohQLb7Z5guBPumYs+/etonmNFlg1Ps6yN9LTPyZn+M+b/9BbnHx3WTMDg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-mock@29.7.0: + resolution: {integrity: sha512-ITOMZn+UkYS4ZFh83xYAOzWStloNzJFO2s8DWrE4lhtGD+AorgnbkiKERe4wQVBydIGPx059g6riW5Btp6Llnw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-mock@30.0.5: resolution: {integrity: sha512-Od7TyasAAQX/6S+QCbN6vZoWOMwlTtzzGuxJku1GhGanAjz9y+QsQkpScDmETvdc9aSXyJ/Op4rhpMYBWW91wQ==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -7256,26 +7768,50 @@ packages: jest-resolve: optional: true + jest-regex-util@29.6.3: + resolution: {integrity: sha512-KJJBsRCyyLNWCNBOvZyRDnAIfUiRJ8v+hOBQYGn8gDyF3UegwiP4gwRR3/SDa42g1YbVycTidUF3rKjyLFDWbg==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-regex-util@30.0.1: resolution: {integrity: sha512-jHEQgBXAgc+Gh4g0p3bCevgRCVRkB4VB70zhoAE48gxeSr1hfUOsM/C2WoJgVL7Eyg//hudYENbm3Ne+/dRVVA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-resolve-dependencies@29.7.0: + resolution: {integrity: sha512-un0zD/6qxJ+S0et7WxeI3H5XSe9lTBBR7bOHCHXkKR6luG5mwDDlIzVQ0V5cZCuoTgEdcdwzTghYkTWfubi+nA==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-resolve-dependencies@30.1.1: resolution: {integrity: sha512-tRtaaoH8Ws1Gn1o/9pedt19dvVgr81WwdmvJSP9Ow3amOUOP2nN9j94u5jC9XlIfa2Q1FQKIWWQwL4ajqsjCGQ==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-resolve@29.7.0: + resolution: {integrity: sha512-IOVhZSrg+UvVAshDSDtHyFCCBUl/Q3AAJv8iZ6ZjnZ74xzvwuzLXid9IIIPgTnY62SJjfuupMKZsZQRsCvxEgA==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-resolve@30.1.0: resolution: {integrity: sha512-hASe7D/wRtZw8Cm607NrlF7fi3HWC5wmA5jCVc2QjQAB2pTwP9eVZILGEi6OeSLNUtE1zb04sXRowsdh5CUjwA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-runner@29.7.0: + resolution: {integrity: sha512-fsc4N6cPCAahybGBfTRcq5wFR6fpLznMg47sY5aDpsoejOcVYFb07AHuSnR0liMcPTgBsA3ZJL6kFOjPdoNipQ==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-runner@30.1.1: resolution: {integrity: sha512-ATe6372SOfJvCRExtCAr06I4rGujwFdKg44b6i7/aOgFnULwjxzugJ0Y4AnG+jeSeQi8dU7R6oqLGmsxRUbErQ==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-runtime@29.7.0: + resolution: {integrity: sha512-gUnLjgwdGqW7B4LvOIkbKs9WGbn+QLqRQQ9juC6HndeDiezIwhDP+mhMwHWCEcfQ5RUXa6OPnFF8BJh5xegwwQ==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-runtime@30.1.1: resolution: {integrity: sha512-7sOyR0Oekw4OesQqqBHuYJRB52QtXiq0NNgLRzVogiMSxKCMiliUd6RrXHCnG5f12Age/ggidCBiQftzcA9XKw==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-snapshot@29.7.0: + resolution: {integrity: sha512-Rm0BMWtxBcioHr1/OX5YCP8Uov4riHvKPknOGs804Zg9JGZgmIBkbtlxJC/7Z4msKYVbIJtfU+tKb8xlYNfdkw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-snapshot@30.1.1: resolution: {integrity: sha512-7/iBEzoJqEt2TjkQY+mPLHP8cbPhLReZVkkxjTMzIzoTC4cZufg7HzKo/n9cIkXKj2LG0x3mmBHsZto+7TOmFg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -7288,10 +7824,18 @@ packages: resolution: {integrity: sha512-pvyPWssDZR0FlfMxCBoc0tvM8iUEskaRFALUtGQYzVEAqisAztmy+R8LnU14KT4XA0H/a5HMVTXat1jLne010g==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-validate@29.7.0: + resolution: {integrity: sha512-ZB7wHqaRGVw/9hST/OuFUReG7M8vKeq0/J2egIGLdvjHCmYqGARhzXmtgi+gVeZ5uXFF219aOc3Ls2yLg27tkw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-validate@30.1.0: resolution: {integrity: sha512-7P3ZlCFW/vhfQ8pE7zW6Oi4EzvuB4sgR72Q1INfW9m0FGo0GADYlPwIkf4CyPq7wq85g+kPMtPOHNAdWHeBOaA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest-watcher@29.7.0: + resolution: {integrity: sha512-49Fg7WXkU3Vl2h6LbLtMQ/HyB6rXSIX7SqvBLQmssRBGN9I0PNvPmAmCWSOY6SOvrjhI/F7/bGAv9RtnsPA03g==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + jest-watcher@30.1.1: resolution: {integrity: sha512-CrAQ73LlaS6KGQQw6NBi71g7qvP7scy+4+2c0jKX6+CWaYg85lZiig5nQQVTsS5a5sffNPL3uxXnaE9d7v9eQg==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -7308,6 +7852,16 @@ packages: resolution: {integrity: sha512-uvWcSjlwAAgIu133Tt77A05H7RIk3Ho8tZL50bQM2AkvLdluw9NG48lRCl3Dt+MOH719n/0nnb5YxUwcuJiKRA==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} + jest@29.7.0: + resolution: {integrity: sha512-NIy3oAFp9shda19hy4HK0HRTWKtPJmGdnvywu01nOqNC2vZg+Z+fvJDxpMQA88eb2I9EcafcdjYgsDthnYTvGw==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + hasBin: true + peerDependencies: + node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 + peerDependenciesMeta: + node-notifier: + optional: true + jest@30.1.1: resolution: {integrity: sha512-yC3JvpP/ZcAZX5rYCtXO/g9k6VTCQz0VFE2v1FpxytWzUqfDtu0XL/pwnNvptzYItvGwomh1ehomRNMOyhCJKw==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -7329,6 +7883,9 @@ packages: joi@17.13.3: resolution: {integrity: sha512-otDA4ldcIx+ZXsKHWmp0YizCweVRZG96J10b0FevjfuncLO1oX59THoAmHkNubYJ+9gWsYsp5k8v4ib6oDv1fA==} + js-sha256@0.11.1: + resolution: {integrity: sha512-o6WSo/LUvY2uC4j7mO50a2ms7E/EAdbP0swigLV+nzHKTTaYnaLIWJ02VdXrsJX0vGedDESQnLsOekr94ryfjg==} + js-tokens@4.0.0: resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} @@ -7557,6 +8114,10 @@ packages: lodash.debounce@4.0.8: resolution: {integrity: sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==} + lodash.isequal@4.5.0: + resolution: {integrity: sha512-pDo3lu8Jhfjqls6GkMgpahsF9kCyayhgykjyLMNFTKWrpVdAQtYyB4muAMWozBB4ig/dtWAmsMxLEI8wuz+DYQ==} + deprecated: This package is deprecated. Use require('node:util').isDeepStrictEqual instead. + lodash.memoize@4.1.2: resolution: {integrity: sha512-t7j+NzmgnQzTAYXcsHYLgimltOV1MXHtlOWf6GjL9Kj8GK5FInw5JotxvbOs+IvV1/Dzo04/fCGfLVs7aXb4Ag==} @@ -7648,6 +8209,9 @@ packages: resolution: {integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==} engines: {node: '>= 0.4'} + md5.js@1.3.5: + resolution: {integrity: sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg==} + mdast-util-directive@3.1.0: resolution: {integrity: sha512-I3fNFt+DHmpWCYAT7quoM6lHf9wuqtI+oCOfvILnoicNIqjh5E3dEJWiXuYME2gNe8vl1iMQwyUHa7bgFmak6Q==} @@ -8892,6 +9456,10 @@ packages: pretty-error@4.0.0: resolution: {integrity: sha512-AoJ5YMAcXKYxKhuJGdcvse+Voc6v1RgnsR3nWcYU7q4t6z0Q6T86sv5Zq8VIRbOWWFpvdGE83LtdSMNd+6Y0xw==} + pretty-format@29.7.0: + resolution: {integrity: sha512-Pdlw/oPxN+aXdmM9R00JVC9WVFoCLTKJvDVLgmJ+qAffBMxsV85l/Lu7sNx4zSzPyoL2euImuEwHhOXdEgNFZQ==} + engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} + pretty-format@30.0.5: resolution: {integrity: sha512-D1tKtYvByrBkFLe2wHJl2bwMJIiT8rW+XA+TiataH79/FszLQMrpGEvzUVkzPau7OCO0Qnrhpe87PqtOAIB8Yw==} engines: {node: ^18.14.0 || ^20.0.0 || ^22.0.0 || >=24.0.0} @@ -8947,6 +9515,9 @@ packages: resolution: {integrity: sha512-FLpr4flz5xZTSJxSeaheeMKN/EDzMdK7b8PTOC6a5PYFKTucWbdqjgqaEyH0shFiSJrVB1+Qqi4Tk19ccU6Aug==} engines: {node: '>=12.20'} + pure-rand@6.1.0: + resolution: {integrity: sha512-bVWawvoZoBYpp6yIoQtQXHZjmz35RSVHnUOTefl8Vcjr8snTPY1wnpSPMWekcFwbxI6gtmT7rSYPFvz71ldiOA==} + pure-rand@7.0.1: resolution: {integrity: sha512-oTUZM/NAZS8p7ANR3SHh30kXB+zK2r2BPcEn/awJIbOvq82WoMN4p62AWWp3Hhw50G0xMsw1mhIBLqHw64EcNQ==} @@ -9226,6 +9797,10 @@ packages: resolve-pkg-maps@1.0.0: resolution: {integrity: sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==} + resolve.exports@2.0.3: + resolution: {integrity: sha512-OcXjMsGdhL4XnbShKpAcSqPMzQoYkYyhbEaeSko47MjRP9NfEQMhZkXL1DoFlt9LWQn4YttrdnV6X2OiyzBi+A==} + engines: {node: '>=10'} + resolve@1.22.10: resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==} engines: {node: '>= 0.4'} @@ -9261,6 +9836,10 @@ packages: engines: {node: 20 || >=22} hasBin: true + ripemd160@2.0.3: + resolution: {integrity: sha512-5Di9UC0+8h1L6ZD2d7awM7E/T4uA1fJRlx6zk/NvdCCVEoAnFqvHmCuNeIKoCeIixBX/q8uM+6ycDvF8woqosA==} + engines: {node: '>= 0.8'} + rollup@4.49.0: resolution: {integrity: sha512-3IVq0cGJ6H7fKXXEdVt+RcYvRCt8beYY9K1760wGQwSAHZcS9eot1zDG5axUbcp/kWRi5zKIIDX8MoKv/TzvZA==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} @@ -9410,6 +9989,11 @@ packages: setprototypeof@1.2.0: resolution: {integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==} + sha.js@2.4.12: + resolution: {integrity: sha512-8LzC5+bvI45BjpfXU8V5fdU2mfeKiQe1D1gIMn7XUlF3OTUrpdJpPPH4EMAnF0DsHHdSZqCdSss5qCmJKuiO3w==} + engines: {node: '>= 0.10'} + hasBin: true + shallow-clone@3.0.1: resolution: {integrity: sha512-/6KqX+GVUdqPuPPd2LxDDxzX6CAbjJehAAOKlNpqqUpAqPM6HeL8f+o3a+JsyGjn2lv0WY8UsTgUJjU9Ok55NA==} engines: {node: '>=8'} @@ -9854,6 +10438,10 @@ packages: tmpl@1.0.5: resolution: {integrity: sha512-3f0uOEAQwIqGuWW2MVzYg8fV/QNnc/IpuJNG837rLuczAaLVHslWHZQj4IGiEl5Hs3kkbhwL9Ab7Hrsmuj+Smw==} + to-buffer@1.2.2: + resolution: {integrity: sha512-db0E3UJjcFhpDhAF4tLo03oli3pwl3dbnzXOUIlRKrp+ldk/VUxzpWYZENsw2SZiuBjHAk7DfB0VU7NKdpb6sw==} + engines: {node: '>= 0.4'} + to-regex-range@5.0.1: resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} engines: {node: '>=8.0'} @@ -9974,6 +10562,11 @@ packages: engines: {node: '>=18.0.0'} hasBin: true + tsx@4.21.0: + resolution: {integrity: sha512-5C1sg4USs1lfG0GFb2RLXsdpXqBSEhAaA/0kPL01wxzpMqLILNxIxIOKiILz+cdg/pLnOUxFYOR5yhHU666wbw==} + engines: {node: '>=18.0.0'} + hasBin: true + type-check@0.4.0: resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} engines: {node: '>= 0.8.0'} @@ -10067,6 +10660,9 @@ packages: peerDependencies: typescript: 5.0.x || 5.1.x || 5.2.x || 5.3.x || 5.4.x || 5.5.x || 5.6.x || 5.7.x || 5.8.x + typeforce@1.18.0: + resolution: {integrity: sha512-7uc1O8h1M1g0rArakJdf0uLRSSgFcYexrVoKo+bzJd32gd4gDy2L/Z+8/FjPnU9ydY3pEnVPtr9FyscYY60K1g==} + typescript-eslint@8.41.0: resolution: {integrity: sha512-n66rzs5OBXW3SFSnZHr2T685q1i4ODm2nulFJhMZBotaTavsS8TrI3d7bDlRSs9yWo7HmyWrN9qDu14Qv7Y0Dw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} @@ -10117,6 +10713,9 @@ packages: undici-types@6.19.8: resolution: {integrity: sha512-ve2KP6f/JnbPBFyobGHuerC9g1FYGn/F8n1LWTwNxCEzd6IfqTwUQcNXgEtmmQ6DlRrC1hrSrBnCZPokRrDHjw==} + undici-types@6.21.0: + resolution: {integrity: sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==} + undici-types@7.10.0: resolution: {integrity: sha512-t5Fy/nfn+14LuOc2KNYg75vZqClpAiqscVvMygNnlsHBFpSXdJaYtXMcdNLpl/Qvc3P2cB3s6lOV51nqsFq4ag==} @@ -10258,6 +10857,9 @@ packages: value-equal@1.0.1: resolution: {integrity: sha512-NOJ6JZCAWr0zlxZt+xqCHNTEKOsrks2HQd4MqhP1qy4z1SkbEP467eNx6TgDKXMvUOb+OENfJCZwM+16n7fRfw==} + varuint-bitcoin@1.1.2: + resolution: {integrity: sha512-4EVb+w4rx+YfVM32HQX42AbbT7/1f5zwAYhIujKXKk8NQK+JfRVl3pqT3hjNn/L+RstigmGGKVwHA/P0wgITZw==} + vary@1.1.2: resolution: {integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==} engines: {node: '>= 0.8'} @@ -10473,6 +11075,9 @@ packages: resolution: {integrity: sha512-o0cyEG0e8GPzT4iGHphIOh0cJOV8fivsXxddQasHPHfoZf1ZexrfeA21w2NaEN1RHE+fXlfISmOE8R9N3u3Qig==} engines: {node: '>=12'} + wif@2.0.6: + resolution: {integrity: sha512-HIanZn1zmduSF+BQhkE+YXIbEiH0xPr1012QbFEGB0xsKqJii0/SqJjyn8dFv6y36kOznMgMB+LGcbZTJ1xACQ==} + wildcard@2.0.1: resolution: {integrity: sha512-CC1bOL87PIWSBhDcTrdeLo6eGT7mCFtrg0uIJtqJUFyK+eJnzl8A1niH56uu7KMa5XFrtiV+AQuHO3n7DsHnLQ==} @@ -10501,6 +11106,10 @@ packages: write-file-atomic@3.0.3: resolution: {integrity: sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==} + write-file-atomic@4.0.2: + resolution: {integrity: sha512-7KxauUdBmSdWnmpaGFg+ppNjKF8uNLry8LyzjauQDOVONfFLNKrKvQOxZ/VuTIcS/gge/YNahf5RIIQWTSarlg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + write-file-atomic@5.0.1: resolution: {integrity: sha512-+QU2zd6OTD8XWIJCbffaiQeH9U73qIqafo1x6V1snCWYGJf6cVE0cDR4D8xRzcEnfI21IFrUPzPGtcPf8AC+Rw==} engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0} @@ -11624,6 +12233,11 @@ snapshots: '@bcoe/v8-coverage@1.0.2': {} + '@bitcoinerlab/secp256k1@1.1.1': + dependencies: + '@noble/hashes': 1.8.0 + '@noble/secp256k1': 1.7.2 + '@borewit/text-codec@0.1.1': {} '@changesets/apply-release-plan@7.0.12': @@ -11785,6 +12399,17 @@ snapshots: human-id: 4.1.1 prettier: 2.8.8 + '@ckb-lumos/base@0.23.0': + dependencies: + '@ckb-lumos/bi': 0.23.0 + '@ckb-lumos/codec': 0.23.0 + '@ckb-lumos/toolkit': 0.23.0 + '@types/blake2b': 2.1.3 + '@types/lodash.isequal': 4.5.8 + blake2b: 2.1.4 + js-xxhash: 1.0.4 + lodash.isequal: 4.5.0 + '@ckb-lumos/base@0.24.0-next.2': dependencies: '@ckb-lumos/bi': 0.24.0-next.2 @@ -11795,6 +12420,10 @@ snapshots: blake2b: 2.1.4 js-xxhash: 1.0.4 + '@ckb-lumos/bi@0.23.0': + dependencies: + jsbi: 4.3.2 + '@ckb-lumos/bi@0.24.0-next.2': dependencies: jsbi: 4.3.2 @@ -11811,6 +12440,10 @@ snapshots: transitivePeerDependencies: - encoding + '@ckb-lumos/codec@0.23.0': + dependencies: + '@ckb-lumos/bi': 0.23.0 + '@ckb-lumos/codec@0.24.0-next.2': dependencies: '@ckb-lumos/bi': 0.24.0-next.2 @@ -11868,6 +12501,10 @@ snapshots: transitivePeerDependencies: - encoding + '@ckb-lumos/toolkit@0.23.0': + dependencies: + '@ckb-lumos/bi': 0.23.0 + '@ckb-lumos/toolkit@0.24.0-next.2': dependencies: '@ckb-lumos/bi': 0.24.0-next.2 @@ -12969,81 +13606,159 @@ snapshots: '@esbuild/aix-ppc64@0.25.9': optional: true + '@esbuild/aix-ppc64@0.27.2': + optional: true + '@esbuild/android-arm64@0.25.9': optional: true + '@esbuild/android-arm64@0.27.2': + optional: true + '@esbuild/android-arm@0.25.9': optional: true + '@esbuild/android-arm@0.27.2': + optional: true + '@esbuild/android-x64@0.25.9': optional: true + '@esbuild/android-x64@0.27.2': + optional: true + '@esbuild/darwin-arm64@0.25.9': optional: true + '@esbuild/darwin-arm64@0.27.2': + optional: true + '@esbuild/darwin-x64@0.25.9': optional: true + '@esbuild/darwin-x64@0.27.2': + optional: true + '@esbuild/freebsd-arm64@0.25.9': optional: true + '@esbuild/freebsd-arm64@0.27.2': + optional: true + '@esbuild/freebsd-x64@0.25.9': optional: true + '@esbuild/freebsd-x64@0.27.2': + optional: true + '@esbuild/linux-arm64@0.25.9': optional: true + '@esbuild/linux-arm64@0.27.2': + optional: true + '@esbuild/linux-arm@0.25.9': optional: true + '@esbuild/linux-arm@0.27.2': + optional: true + '@esbuild/linux-ia32@0.25.9': optional: true + '@esbuild/linux-ia32@0.27.2': + optional: true + '@esbuild/linux-loong64@0.25.9': optional: true + '@esbuild/linux-loong64@0.27.2': + optional: true + '@esbuild/linux-mips64el@0.25.9': optional: true + '@esbuild/linux-mips64el@0.27.2': + optional: true + '@esbuild/linux-ppc64@0.25.9': optional: true + '@esbuild/linux-ppc64@0.27.2': + optional: true + '@esbuild/linux-riscv64@0.25.9': optional: true + '@esbuild/linux-riscv64@0.27.2': + optional: true + '@esbuild/linux-s390x@0.25.9': optional: true + '@esbuild/linux-s390x@0.27.2': + optional: true + '@esbuild/linux-x64@0.25.9': optional: true + '@esbuild/linux-x64@0.27.2': + optional: true + '@esbuild/netbsd-arm64@0.25.9': optional: true + '@esbuild/netbsd-arm64@0.27.2': + optional: true + '@esbuild/netbsd-x64@0.25.9': optional: true + '@esbuild/netbsd-x64@0.27.2': + optional: true + '@esbuild/openbsd-arm64@0.25.9': optional: true + '@esbuild/openbsd-arm64@0.27.2': + optional: true + '@esbuild/openbsd-x64@0.25.9': optional: true + '@esbuild/openbsd-x64@0.27.2': + optional: true + '@esbuild/openharmony-arm64@0.25.9': optional: true + '@esbuild/openharmony-arm64@0.27.2': + optional: true + '@esbuild/sunos-x64@0.25.9': optional: true + '@esbuild/sunos-x64@0.27.2': + optional: true + '@esbuild/win32-arm64@0.25.9': optional: true + '@esbuild/win32-arm64@0.27.2': + optional: true + '@esbuild/win32-ia32@0.25.9': optional: true + '@esbuild/win32-ia32@0.27.2': + optional: true + '@esbuild/win32-x64@0.25.9': optional: true + '@esbuild/win32-x64@0.27.2': + optional: true + '@eslint-community/eslint-utils@4.7.0(eslint@8.57.1)': dependencies: eslint: 8.57.1 @@ -13125,6 +13840,8 @@ snapshots: - supports-color - typescript + '@exact-realty/multipart-parser@1.0.14': {} + '@floating-ui/core@1.7.3': dependencies: '@floating-ui/utils': 0.2.10 @@ -13465,6 +14182,15 @@ snapshots: '@istanbuljs/schema@0.1.3': {} + '@jest/console@29.7.0': + dependencies: + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + chalk: 4.1.2 + jest-message-util: 29.7.0 + jest-util: 29.7.0 + slash: 3.0.0 + '@jest/console@30.1.1': dependencies: '@jest/types': 30.0.5 @@ -13474,6 +14200,41 @@ snapshots: jest-util: 30.0.5 slash: 3.0.0 + '@jest/core@29.7.0(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2))': + dependencies: + '@jest/console': 29.7.0 + '@jest/reporters': 29.7.0 + '@jest/test-result': 29.7.0 + '@jest/transform': 29.7.0 + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + ansi-escapes: 4.3.2 + chalk: 4.1.2 + ci-info: 3.9.0 + exit: 0.1.2 + graceful-fs: 4.2.11 + jest-changed-files: 29.7.0 + jest-config: 29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + jest-haste-map: 29.7.0 + jest-message-util: 29.7.0 + jest-regex-util: 29.6.3 + jest-resolve: 29.7.0 + jest-resolve-dependencies: 29.7.0 + jest-runner: 29.7.0 + jest-runtime: 29.7.0 + jest-snapshot: 29.7.0 + jest-util: 29.7.0 + jest-validate: 29.7.0 + jest-watcher: 29.7.0 + micromatch: 4.0.8 + pretty-format: 29.7.0 + slash: 3.0.0 + strip-ansi: 6.0.1 + transitivePeerDependencies: + - babel-plugin-macros + - supports-color + - ts-node + '@jest/core@30.1.1(ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2))': dependencies: '@jest/console': 30.1.1 @@ -13512,6 +14273,13 @@ snapshots: '@jest/diff-sequences@30.0.1': {} + '@jest/environment@29.7.0': + dependencies: + '@jest/fake-timers': 29.7.0 + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + jest-mock: 29.7.0 + '@jest/environment@30.1.1': dependencies: '@jest/fake-timers': 30.1.1 @@ -13519,10 +14287,21 @@ snapshots: '@types/node': 24.3.0 jest-mock: 30.0.5 + '@jest/expect-utils@29.7.0': + dependencies: + jest-get-type: 29.6.3 + '@jest/expect-utils@30.1.1': dependencies: '@jest/get-type': 30.1.0 + '@jest/expect@29.7.0': + dependencies: + expect: 29.7.0 + jest-snapshot: 29.7.0 + transitivePeerDependencies: + - supports-color + '@jest/expect@30.1.1': dependencies: expect: 30.1.1 @@ -13530,6 +14309,15 @@ snapshots: transitivePeerDependencies: - supports-color + '@jest/fake-timers@29.7.0': + dependencies: + '@jest/types': 29.6.3 + '@sinonjs/fake-timers': 10.3.0 + '@types/node': 22.19.3 + jest-message-util: 29.7.0 + jest-mock: 29.7.0 + jest-util: 29.7.0 + '@jest/fake-timers@30.1.1': dependencies: '@jest/types': 30.0.5 @@ -13541,6 +14329,15 @@ snapshots: '@jest/get-type@30.1.0': {} + '@jest/globals@29.7.0': + dependencies: + '@jest/environment': 29.7.0 + '@jest/expect': 29.7.0 + '@jest/types': 29.6.3 + jest-mock: 29.7.0 + transitivePeerDependencies: + - supports-color + '@jest/globals@30.1.1': dependencies: '@jest/environment': 30.1.1 @@ -13555,6 +14352,35 @@ snapshots: '@types/node': 24.3.0 jest-regex-util: 30.0.1 + '@jest/reporters@29.7.0': + dependencies: + '@bcoe/v8-coverage': 0.2.3 + '@jest/console': 29.7.0 + '@jest/test-result': 29.7.0 + '@jest/transform': 29.7.0 + '@jest/types': 29.6.3 + '@jridgewell/trace-mapping': 0.3.30 + '@types/node': 22.19.3 + chalk: 4.1.2 + collect-v8-coverage: 1.0.2 + exit: 0.1.2 + glob: 7.2.3 + graceful-fs: 4.2.11 + istanbul-lib-coverage: 3.2.2 + istanbul-lib-instrument: 6.0.3 + istanbul-lib-report: 3.0.1 + istanbul-lib-source-maps: 4.0.1 + istanbul-reports: 3.2.0 + jest-message-util: 29.7.0 + jest-util: 29.7.0 + jest-worker: 29.7.0 + slash: 3.0.0 + string-length: 4.0.2 + strip-ansi: 6.0.1 + v8-to-istanbul: 9.3.0 + transitivePeerDependencies: + - supports-color + '@jest/reporters@30.1.1': dependencies: '@bcoe/v8-coverage': 0.2.3 @@ -13598,12 +14424,25 @@ snapshots: graceful-fs: 4.2.11 natural-compare: 1.4.0 + '@jest/source-map@29.6.3': + dependencies: + '@jridgewell/trace-mapping': 0.3.30 + callsites: 3.1.0 + graceful-fs: 4.2.11 + '@jest/source-map@30.0.1': dependencies: '@jridgewell/trace-mapping': 0.3.30 callsites: 3.1.0 graceful-fs: 4.2.11 + '@jest/test-result@29.7.0': + dependencies: + '@jest/console': 29.7.0 + '@jest/types': 29.6.3 + '@types/istanbul-lib-coverage': 2.0.6 + collect-v8-coverage: 1.0.2 + '@jest/test-result@30.1.1': dependencies: '@jest/console': 30.1.1 @@ -13611,6 +14450,13 @@ snapshots: '@types/istanbul-lib-coverage': 2.0.6 collect-v8-coverage: 1.0.2 + '@jest/test-sequencer@29.7.0': + dependencies: + '@jest/test-result': 29.7.0 + graceful-fs: 4.2.11 + jest-haste-map: 29.7.0 + slash: 3.0.0 + '@jest/test-sequencer@30.1.1': dependencies: '@jest/test-result': 30.1.1 @@ -13618,6 +14464,26 @@ snapshots: jest-haste-map: 30.1.0 slash: 3.0.0 + '@jest/transform@29.7.0': + dependencies: + '@babel/core': 7.28.3 + '@jest/types': 29.6.3 + '@jridgewell/trace-mapping': 0.3.30 + babel-plugin-istanbul: 6.1.1 + chalk: 4.1.2 + convert-source-map: 2.0.0 + fast-json-stable-stringify: 2.1.0 + graceful-fs: 4.2.11 + jest-haste-map: 29.7.0 + jest-regex-util: 29.6.3 + jest-util: 29.7.0 + micromatch: 4.0.8 + pirates: 4.0.7 + slash: 3.0.0 + write-file-atomic: 4.0.2 + transitivePeerDependencies: + - supports-color + '@jest/transform@30.1.1': dependencies: '@babel/core': 7.28.3 @@ -13643,7 +14509,7 @@ snapshots: '@jest/schemas': 29.6.3 '@types/istanbul-lib-coverage': 2.0.6 '@types/istanbul-reports': 3.0.4 - '@types/node': 24.3.0 + '@types/node': 22.19.3 '@types/yargs': 17.0.33 chalk: 4.1.2 @@ -14011,6 +14877,8 @@ snapshots: '@noble/hashes@2.0.0': {} + '@noble/secp256k1@1.7.2': {} + '@nodelib/fs.scandir@2.1.5': dependencies: '@nodelib/fs.stat': 2.0.5 @@ -14163,6 +15031,8 @@ snapshots: '@rtsao/scc@1.1.0': {} + '@scure/base@1.2.6': {} + '@scure/base@2.0.0': {} '@scure/bip32@2.0.0': @@ -14240,6 +15110,10 @@ snapshots: dependencies: type-detect: 4.0.8 + '@sinonjs/fake-timers@10.3.0': + dependencies: + '@sinonjs/commons': 3.0.1 + '@sinonjs/fake-timers@13.0.5': dependencies: '@sinonjs/commons': 3.0.1 @@ -14568,6 +15442,10 @@ snapshots: '@types/express-serve-static-core': 5.0.7 '@types/serve-static': 1.15.8 + '@types/graceful-fs@4.1.9': + dependencies: + '@types/node': 22.19.3 + '@types/gtag.js@0.0.12': {} '@types/hast@3.0.4': @@ -14596,6 +15474,11 @@ snapshots: dependencies: '@types/istanbul-lib-report': 3.0.3 + '@types/jest@29.5.14': + dependencies: + expect: 29.7.0 + pretty-format: 29.7.0 + '@types/jest@30.0.0': dependencies: expect: 30.1.1 @@ -14633,7 +15516,11 @@ snapshots: '@types/node@17.0.45': {} - '@types/node@22.7.5': + '@types/node@22.19.3': + dependencies: + undici-types: 6.21.0 + + '@types/node@22.7.5': dependencies: undici-types: 6.19.8 @@ -15072,7 +15959,7 @@ snapshots: '@unrs/resolver-binding-win32-x64-msvc@1.11.1': optional: true - '@vitest/coverage-v8@3.2.4(vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1))': + '@vitest/coverage-v8@3.2.4(vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1))': dependencies: '@ampproject/remapping': 2.3.0 '@bcoe/v8-coverage': 1.0.2 @@ -15087,7 +15974,7 @@ snapshots: std-env: 3.9.0 test-exclude: 7.0.1 tinyrainbow: 2.0.0 - vitest: 3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1) + vitest: 3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1) transitivePeerDependencies: - supports-color @@ -15099,13 +15986,13 @@ snapshots: chai: 5.3.3 tinyrainbow: 2.0.0 - '@vitest/mocker@3.2.4(vite@7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1))': + '@vitest/mocker@3.2.4(vite@7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1))': dependencies: '@vitest/spy': 3.2.4 estree-walker: 3.0.3 magic-string: 0.30.18 optionalDependencies: - vite: 7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1) + vite: 7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1) '@vitest/pretty-format@3.2.4': dependencies: @@ -15475,6 +16362,19 @@ snapshots: b4a@1.6.7: {} + babel-jest@29.7.0(@babel/core@7.28.3): + dependencies: + '@babel/core': 7.28.3 + '@jest/transform': 29.7.0 + '@types/babel__core': 7.20.5 + babel-plugin-istanbul: 6.1.1 + babel-preset-jest: 29.6.3(@babel/core@7.28.3) + chalk: 4.1.2 + graceful-fs: 4.2.11 + slash: 3.0.0 + transitivePeerDependencies: + - supports-color + babel-jest@30.1.1(@babel/core@7.28.3): dependencies: '@babel/core': 7.28.3 @@ -15499,6 +16399,16 @@ snapshots: dependencies: object.assign: 4.1.7 + babel-plugin-istanbul@6.1.1: + dependencies: + '@babel/helper-plugin-utils': 7.27.1 + '@istanbuljs/load-nyc-config': 1.1.0 + '@istanbuljs/schema': 0.1.3 + istanbul-lib-instrument: 5.2.1 + test-exclude: 6.0.0 + transitivePeerDependencies: + - supports-color + babel-plugin-istanbul@7.0.0: dependencies: '@babel/helper-plugin-utils': 7.27.1 @@ -15509,6 +16419,13 @@ snapshots: transitivePeerDependencies: - supports-color + babel-plugin-jest-hoist@29.6.3: + dependencies: + '@babel/template': 7.27.2 + '@babel/types': 7.28.2 + '@types/babel__core': 7.20.5 + '@types/babel__traverse': 7.28.0 + babel-plugin-jest-hoist@30.0.1: dependencies: '@babel/template': 7.27.2 @@ -15558,6 +16475,12 @@ snapshots: '@babel/plugin-syntax-private-property-in-object': 7.14.5(@babel/core@7.28.3) '@babel/plugin-syntax-top-level-await': 7.14.5(@babel/core@7.28.3) + babel-preset-jest@29.6.3(@babel/core@7.28.3): + dependencies: + '@babel/core': 7.28.3 + babel-plugin-jest-hoist: 29.6.3 + babel-preset-current-node-syntax: 1.2.0(@babel/core@7.28.3) + babel-preset-jest@30.0.1(@babel/core@7.28.3): dependencies: '@babel/core': 7.28.3 @@ -15568,6 +16491,10 @@ snapshots: balanced-match@1.0.2: {} + base-x@3.0.11: + dependencies: + safe-buffer: 5.2.1 + base-x@4.0.1: {} base-x@5.0.1: {} @@ -15588,6 +16515,24 @@ snapshots: binary-extensions@2.3.0: {} + bip174@2.1.1: {} + + bip32@4.0.0: + dependencies: + '@noble/hashes': 1.8.0 + '@scure/base': 1.2.6 + typeforce: 1.18.0 + wif: 2.0.6 + + bitcoinjs-lib@6.1.6: + dependencies: + '@noble/hashes': 1.8.0 + bech32: 2.0.0 + bip174: 2.1.1 + bs58check: 3.0.1 + typeforce: 1.18.0 + varuint-bitcoin: 1.1.2 + bl@4.1.0: dependencies: buffer: 5.7.1 @@ -15692,6 +16637,10 @@ snapshots: dependencies: fast-json-stable-stringify: 2.1.0 + bs58@4.0.1: + dependencies: + base-x: 3.0.11 + bs58@5.0.0: dependencies: base-x: 4.0.1 @@ -15700,6 +16649,17 @@ snapshots: dependencies: base-x: 5.0.1 + bs58check@2.1.2: + dependencies: + bs58: 4.0.1 + create-hash: 1.2.0 + safe-buffer: 5.2.1 + + bs58check@3.0.1: + dependencies: + '@noble/hashes': 1.8.0 + bs58: 5.0.0 + bs58check@4.0.0(patch_hash=0848a2e3956f24abf1dd8620cba2a3f468393e489185d9536ad109f7e5712d26): dependencies: '@noble/hashes': 1.8.0 @@ -15870,6 +16830,14 @@ snapshots: ci-info@4.3.0: {} + cipher-base@1.0.7: + dependencies: + inherits: 2.0.4 + safe-buffer: 5.2.1 + to-buffer: 1.2.2 + + cjs-module-lexer@1.4.3: {} + cjs-module-lexer@2.1.0: {} class-transformer@0.5.1: {} @@ -16103,6 +17071,29 @@ snapshots: optionalDependencies: typescript: 5.9.2 + create-hash@1.2.0: + dependencies: + cipher-base: 1.0.7 + inherits: 2.0.4 + md5.js: 1.3.5 + ripemd160: 2.0.3 + sha.js: 2.4.12 + + create-jest@29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)): + dependencies: + '@jest/types': 29.6.3 + chalk: 4.1.2 + exit: 0.1.2 + graceful-fs: 4.2.11 + jest-config: 29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + jest-util: 29.7.0 + prompts: 2.4.2 + transitivePeerDependencies: + - '@types/node' + - babel-plugin-macros + - supports-color + - ts-node + create-require@1.1.1: {} cross-fetch@3.2.0: @@ -16405,6 +17396,8 @@ snapshots: asap: 2.0.6 wrappy: 1.0.2 + diff-sequences@29.6.3: {} + diff@4.0.2: {} dir-glob@3.0.1: @@ -16490,6 +17483,12 @@ snapshots: eastasianwidth@0.2.0: {} + ecpair@2.1.0: + dependencies: + randombytes: 2.1.0 + typeforce: 1.18.0 + wif: 2.0.6 + ee-first@1.1.1: {} electron-to-chromium@1.5.211: {} @@ -16688,6 +17687,35 @@ snapshots: '@esbuild/win32-ia32': 0.25.9 '@esbuild/win32-x64': 0.25.9 + esbuild@0.27.2: + optionalDependencies: + '@esbuild/aix-ppc64': 0.27.2 + '@esbuild/android-arm': 0.27.2 + '@esbuild/android-arm64': 0.27.2 + '@esbuild/android-x64': 0.27.2 + '@esbuild/darwin-arm64': 0.27.2 + '@esbuild/darwin-x64': 0.27.2 + '@esbuild/freebsd-arm64': 0.27.2 + '@esbuild/freebsd-x64': 0.27.2 + '@esbuild/linux-arm': 0.27.2 + '@esbuild/linux-arm64': 0.27.2 + '@esbuild/linux-ia32': 0.27.2 + '@esbuild/linux-loong64': 0.27.2 + '@esbuild/linux-mips64el': 0.27.2 + '@esbuild/linux-ppc64': 0.27.2 + '@esbuild/linux-riscv64': 0.27.2 + '@esbuild/linux-s390x': 0.27.2 + '@esbuild/linux-x64': 0.27.2 + '@esbuild/netbsd-arm64': 0.27.2 + '@esbuild/netbsd-x64': 0.27.2 + '@esbuild/openbsd-arm64': 0.27.2 + '@esbuild/openbsd-x64': 0.27.2 + '@esbuild/openharmony-arm64': 0.27.2 + '@esbuild/sunos-x64': 0.27.2 + '@esbuild/win32-arm64': 0.27.2 + '@esbuild/win32-ia32': 0.27.2 + '@esbuild/win32-x64': 0.27.2 + escalade@3.2.0: {} escape-goat@4.0.0: {} @@ -16707,28 +17735,8 @@ snapshots: '@next/eslint-plugin-next': 16.0.10 eslint: 9.34.0(jiti@2.5.1) eslint-import-resolver-node: 0.3.9 - eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.32.0)(eslint@9.34.0(jiti@2.5.1)) - eslint-plugin-import: 2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1)(eslint@9.34.0(jiti@2.5.1)) - eslint-plugin-jsx-a11y: 6.10.2(eslint@9.34.0(jiti@2.5.1)) - eslint-plugin-react: 7.37.5(eslint@9.34.0(jiti@2.5.1)) - eslint-plugin-react-hooks: 7.0.1(eslint@9.34.0(jiti@2.5.1)) - globals: 16.4.0 - typescript-eslint: 8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) - optionalDependencies: - typescript: 5.9.2 - transitivePeerDependencies: - - '@typescript-eslint/parser' - - eslint-import-resolver-webpack - - eslint-plugin-import-x - - supports-color - - eslint-config-next@16.0.10(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2): - dependencies: - '@next/eslint-plugin-next': 16.0.10 - eslint: 9.34.0(jiti@2.5.1) - eslint-import-resolver-node: 0.3.9 - eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) - eslint-plugin-import: 2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) + eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) + eslint-plugin-import: 2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) eslint-plugin-jsx-a11y: 6.10.2(eslint@9.34.0(jiti@2.5.1)) eslint-plugin-react: 7.37.5(eslint@9.34.0(jiti@2.5.1)) eslint-plugin-react-hooks: 7.0.1(eslint@9.34.0(jiti@2.5.1)) @@ -16763,22 +17771,7 @@ snapshots: transitivePeerDependencies: - supports-color - eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)): - dependencies: - '@nolyfill/is-core-module': 1.0.39 - debug: 4.4.1 - eslint: 9.34.0(jiti@2.5.1) - get-tsconfig: 4.10.1 - is-bun-module: 2.0.0 - stable-hash: 0.0.5 - tinyglobby: 0.2.14 - unrs-resolver: 1.11.1 - optionalDependencies: - eslint-plugin-import: 2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) - transitivePeerDependencies: - - supports-color - - eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0)(eslint@9.34.0(jiti@2.5.1)): + eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)): dependencies: '@nolyfill/is-core-module': 1.0.39 debug: 4.4.1 @@ -16789,33 +17782,22 @@ snapshots: tinyglobby: 0.2.14 unrs-resolver: 1.11.1 optionalDependencies: - eslint-plugin-import: 2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1)(eslint@9.34.0(jiti@2.5.1)) + eslint-plugin-import: 2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) transitivePeerDependencies: - supports-color - eslint-module-utils@2.12.1(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1)(eslint@9.34.0(jiti@2.5.1)): + eslint-module-utils@2.12.1(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)): dependencies: debug: 3.2.7 optionalDependencies: '@typescript-eslint/parser': 6.21.0(eslint@8.57.1)(typescript@5.9.2) eslint: 9.34.0(jiti@2.5.1) eslint-import-resolver-node: 0.3.9 - eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.32.0)(eslint@9.34.0(jiti@2.5.1)) + eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) transitivePeerDependencies: - supports-color - eslint-module-utils@2.12.1(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)): - dependencies: - debug: 3.2.7 - optionalDependencies: - '@typescript-eslint/parser': 8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) - eslint: 9.34.0(jiti@2.5.1) - eslint-import-resolver-node: 0.3.9 - eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) - transitivePeerDependencies: - - supports-color - - eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1)(eslint@9.34.0(jiti@2.5.1)): + eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)): dependencies: '@rtsao/scc': 1.1.0 array-includes: 3.1.9 @@ -16826,7 +17808,7 @@ snapshots: doctrine: 2.1.0 eslint: 9.34.0(jiti@2.5.1) eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.12.1(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1)(eslint@9.34.0(jiti@2.5.1)) + eslint-module-utils: 2.12.1(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@6.21.0(eslint@8.57.1)(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) hasown: 2.0.2 is-core-module: 2.16.1 is-glob: 4.0.3 @@ -16844,35 +17826,6 @@ snapshots: - eslint-import-resolver-webpack - supports-color - eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)): - dependencies: - '@rtsao/scc': 1.1.0 - array-includes: 3.1.9 - array.prototype.findlastindex: 1.2.6 - array.prototype.flat: 1.3.3 - array.prototype.flatmap: 1.3.3 - debug: 3.2.7 - doctrine: 2.1.0 - eslint: 9.34.0(jiti@2.5.1) - eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.12.1(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)))(eslint@9.34.0(jiti@2.5.1)) - hasown: 2.0.2 - is-core-module: 2.16.1 - is-glob: 4.0.3 - minimatch: 3.1.2 - object.fromentries: 2.0.8 - object.groupby: 1.0.3 - object.values: 1.2.1 - semver: 6.3.1 - string.prototype.trimend: 1.0.9 - tsconfig-paths: 3.15.0 - optionalDependencies: - '@typescript-eslint/parser': 8.49.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) - transitivePeerDependencies: - - eslint-import-resolver-typescript - - eslint-import-resolver-webpack - - supports-color - eslint-plugin-jsx-a11y@6.10.2(eslint@9.34.0(jiti@2.5.1)): dependencies: aria-query: 5.3.2 @@ -17190,8 +18143,18 @@ snapshots: exit-x@0.2.2: {} + exit@0.1.2: {} + expect-type@1.2.2: {} + expect@29.7.0: + dependencies: + '@jest/expect-utils': 29.7.0 + jest-get-type: 29.6.3 + jest-matcher-utils: 29.7.0 + jest-message-util: 29.7.0 + jest-util: 29.7.0 + expect@30.1.1: dependencies: '@jest/expect-utils': 30.1.1 @@ -17705,6 +18668,13 @@ snapshots: has-yarn@3.0.0: {} + hash-base@3.1.2: + dependencies: + inherits: 2.0.4 + readable-stream: 2.3.8 + safe-buffer: 5.2.1 + to-buffer: 1.2.2 + hash.js@1.1.7: dependencies: inherits: 2.0.4 @@ -18250,6 +19220,16 @@ snapshots: istanbul-lib-coverage@3.2.2: {} + istanbul-lib-instrument@5.2.1: + dependencies: + '@babel/core': 7.28.3 + '@babel/parser': 7.28.3 + '@istanbuljs/schema': 0.1.3 + istanbul-lib-coverage: 3.2.2 + semver: 6.3.1 + transitivePeerDependencies: + - supports-color + istanbul-lib-instrument@6.0.3: dependencies: '@babel/core': 7.28.3 @@ -18266,6 +19246,14 @@ snapshots: make-dir: 4.0.0 supports-color: 7.2.0 + istanbul-lib-source-maps@4.0.1: + dependencies: + debug: 4.4.1 + istanbul-lib-coverage: 3.2.2 + source-map: 0.6.1 + transitivePeerDependencies: + - supports-color + istanbul-lib-source-maps@5.0.6: dependencies: '@jridgewell/trace-mapping': 0.3.30 @@ -18300,12 +19288,44 @@ snapshots: dependencies: '@isaacs/cliui': 8.0.2 + jest-changed-files@29.7.0: + dependencies: + execa: 5.1.1 + jest-util: 29.7.0 + p-limit: 3.1.0 + jest-changed-files@30.0.5: dependencies: execa: 5.1.1 jest-util: 30.0.5 p-limit: 3.1.0 + jest-circus@29.7.0: + dependencies: + '@jest/environment': 29.7.0 + '@jest/expect': 29.7.0 + '@jest/test-result': 29.7.0 + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + chalk: 4.1.2 + co: 4.6.0 + dedent: 1.6.0 + is-generator-fn: 2.1.0 + jest-each: 29.7.0 + jest-matcher-utils: 29.7.0 + jest-message-util: 29.7.0 + jest-runtime: 29.7.0 + jest-snapshot: 29.7.0 + jest-util: 29.7.0 + p-limit: 3.1.0 + pretty-format: 29.7.0 + pure-rand: 6.1.0 + slash: 3.0.0 + stack-utils: 2.0.6 + transitivePeerDependencies: + - babel-plugin-macros + - supports-color + jest-circus@30.1.1: dependencies: '@jest/environment': 30.1.1 @@ -18332,6 +19352,25 @@ snapshots: - babel-plugin-macros - supports-color + jest-cli@29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)): + dependencies: + '@jest/core': 29.7.0(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + '@jest/test-result': 29.7.0 + '@jest/types': 29.6.3 + chalk: 4.1.2 + create-jest: 29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + exit: 0.1.2 + import-local: 3.2.0 + jest-config: 29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + jest-util: 29.7.0 + jest-validate: 29.7.0 + yargs: 17.7.2 + transitivePeerDependencies: + - '@types/node' + - babel-plugin-macros + - supports-color + - ts-node + jest-cli@30.1.1(@types/node@24.3.0)(ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2)): dependencies: '@jest/core': 30.1.1(ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2)) @@ -18351,6 +19390,37 @@ snapshots: - supports-color - ts-node + jest-config@29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)): + dependencies: + '@babel/core': 7.28.3 + '@jest/test-sequencer': 29.7.0 + '@jest/types': 29.6.3 + babel-jest: 29.7.0(@babel/core@7.28.3) + chalk: 4.1.2 + ci-info: 3.9.0 + deepmerge: 4.3.1 + glob: 7.2.3 + graceful-fs: 4.2.11 + jest-circus: 29.7.0 + jest-environment-node: 29.7.0 + jest-get-type: 29.6.3 + jest-regex-util: 29.6.3 + jest-resolve: 29.7.0 + jest-runner: 29.7.0 + jest-util: 29.7.0 + jest-validate: 29.7.0 + micromatch: 4.0.8 + parse-json: 5.2.0 + pretty-format: 29.7.0 + slash: 3.0.0 + strip-json-comments: 3.1.1 + optionalDependencies: + '@types/node': 22.19.3 + ts-node: 10.9.2(@types/node@22.19.3)(typescript@5.9.2) + transitivePeerDependencies: + - babel-plugin-macros + - supports-color + jest-config@30.1.1(@types/node@24.3.0)(ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2)): dependencies: '@babel/core': 7.28.3 @@ -18384,6 +19454,13 @@ snapshots: - babel-plugin-macros - supports-color + jest-diff@29.7.0: + dependencies: + chalk: 4.1.2 + diff-sequences: 29.6.3 + jest-get-type: 29.6.3 + pretty-format: 29.7.0 + jest-diff@30.1.1: dependencies: '@jest/diff-sequences': 30.0.1 @@ -18391,10 +19468,22 @@ snapshots: chalk: 4.1.2 pretty-format: 30.0.5 + jest-docblock@29.7.0: + dependencies: + detect-newline: 3.1.0 + jest-docblock@30.0.1: dependencies: detect-newline: 3.1.0 + jest-each@29.7.0: + dependencies: + '@jest/types': 29.6.3 + chalk: 4.1.2 + jest-get-type: 29.6.3 + jest-util: 29.7.0 + pretty-format: 29.7.0 + jest-each@30.1.0: dependencies: '@jest/get-type': 30.1.0 @@ -18403,6 +19492,15 @@ snapshots: jest-util: 30.0.5 pretty-format: 30.0.5 + jest-environment-node@29.7.0: + dependencies: + '@jest/environment': 29.7.0 + '@jest/fake-timers': 29.7.0 + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + jest-mock: 29.7.0 + jest-util: 29.7.0 + jest-environment-node@30.1.1: dependencies: '@jest/environment': 30.1.1 @@ -18413,6 +19511,24 @@ snapshots: jest-util: 30.0.5 jest-validate: 30.1.0 + jest-get-type@29.6.3: {} + + jest-haste-map@29.7.0: + dependencies: + '@jest/types': 29.6.3 + '@types/graceful-fs': 4.1.9 + '@types/node': 22.19.3 + anymatch: 3.1.3 + fb-watchman: 2.0.2 + graceful-fs: 4.2.11 + jest-regex-util: 29.6.3 + jest-util: 29.7.0 + jest-worker: 29.7.0 + micromatch: 4.0.8 + walker: 1.0.8 + optionalDependencies: + fsevents: 2.3.3 + jest-haste-map@30.1.0: dependencies: '@jest/types': 30.0.5 @@ -18428,11 +19544,23 @@ snapshots: optionalDependencies: fsevents: 2.3.3 + jest-leak-detector@29.7.0: + dependencies: + jest-get-type: 29.6.3 + pretty-format: 29.7.0 + jest-leak-detector@30.1.0: dependencies: '@jest/get-type': 30.1.0 pretty-format: 30.0.5 + jest-matcher-utils@29.7.0: + dependencies: + chalk: 4.1.2 + jest-diff: 29.7.0 + jest-get-type: 29.6.3 + pretty-format: 29.7.0 + jest-matcher-utils@30.1.1: dependencies: '@jest/get-type': 30.1.0 @@ -18440,6 +19568,18 @@ snapshots: jest-diff: 30.1.1 pretty-format: 30.0.5 + jest-message-util@29.7.0: + dependencies: + '@babel/code-frame': 7.27.1 + '@jest/types': 29.6.3 + '@types/stack-utils': 2.0.3 + chalk: 4.1.2 + graceful-fs: 4.2.11 + micromatch: 4.0.8 + pretty-format: 29.7.0 + slash: 3.0.0 + stack-utils: 2.0.6 + jest-message-util@30.1.0: dependencies: '@babel/code-frame': 7.27.1 @@ -18452,18 +19592,37 @@ snapshots: slash: 3.0.0 stack-utils: 2.0.6 + jest-mock@29.7.0: + dependencies: + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + jest-util: 29.7.0 + jest-mock@30.0.5: dependencies: '@jest/types': 30.0.5 '@types/node': 24.3.0 jest-util: 30.0.5 + jest-pnp-resolver@1.2.3(jest-resolve@29.7.0): + optionalDependencies: + jest-resolve: 29.7.0 + jest-pnp-resolver@1.2.3(jest-resolve@30.1.0): optionalDependencies: jest-resolve: 30.1.0 + jest-regex-util@29.6.3: {} + jest-regex-util@30.0.1: {} + jest-resolve-dependencies@29.7.0: + dependencies: + jest-regex-util: 29.6.3 + jest-snapshot: 29.7.0 + transitivePeerDependencies: + - supports-color + jest-resolve-dependencies@30.1.1: dependencies: jest-regex-util: 30.0.1 @@ -18471,6 +19630,18 @@ snapshots: transitivePeerDependencies: - supports-color + jest-resolve@29.7.0: + dependencies: + chalk: 4.1.2 + graceful-fs: 4.2.11 + jest-haste-map: 29.7.0 + jest-pnp-resolver: 1.2.3(jest-resolve@29.7.0) + jest-util: 29.7.0 + jest-validate: 29.7.0 + resolve: 1.22.10 + resolve.exports: 2.0.3 + slash: 3.0.0 + jest-resolve@30.1.0: dependencies: chalk: 4.1.2 @@ -18482,6 +19653,32 @@ snapshots: slash: 3.0.0 unrs-resolver: 1.11.1 + jest-runner@29.7.0: + dependencies: + '@jest/console': 29.7.0 + '@jest/environment': 29.7.0 + '@jest/test-result': 29.7.0 + '@jest/transform': 29.7.0 + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + chalk: 4.1.2 + emittery: 0.13.1 + graceful-fs: 4.2.11 + jest-docblock: 29.7.0 + jest-environment-node: 29.7.0 + jest-haste-map: 29.7.0 + jest-leak-detector: 29.7.0 + jest-message-util: 29.7.0 + jest-resolve: 29.7.0 + jest-runtime: 29.7.0 + jest-util: 29.7.0 + jest-watcher: 29.7.0 + jest-worker: 29.7.0 + p-limit: 3.1.0 + source-map-support: 0.5.13 + transitivePeerDependencies: + - supports-color + jest-runner@30.1.1: dependencies: '@jest/console': 30.1.1 @@ -18509,6 +19706,33 @@ snapshots: transitivePeerDependencies: - supports-color + jest-runtime@29.7.0: + dependencies: + '@jest/environment': 29.7.0 + '@jest/fake-timers': 29.7.0 + '@jest/globals': 29.7.0 + '@jest/source-map': 29.6.3 + '@jest/test-result': 29.7.0 + '@jest/transform': 29.7.0 + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + chalk: 4.1.2 + cjs-module-lexer: 1.4.3 + collect-v8-coverage: 1.0.2 + glob: 7.2.3 + graceful-fs: 4.2.11 + jest-haste-map: 29.7.0 + jest-message-util: 29.7.0 + jest-mock: 29.7.0 + jest-regex-util: 29.6.3 + jest-resolve: 29.7.0 + jest-snapshot: 29.7.0 + jest-util: 29.7.0 + slash: 3.0.0 + strip-bom: 4.0.0 + transitivePeerDependencies: + - supports-color + jest-runtime@30.1.1: dependencies: '@jest/environment': 30.1.1 @@ -18536,6 +19760,31 @@ snapshots: transitivePeerDependencies: - supports-color + jest-snapshot@29.7.0: + dependencies: + '@babel/core': 7.28.3 + '@babel/generator': 7.28.3 + '@babel/plugin-syntax-jsx': 7.27.1(@babel/core@7.28.3) + '@babel/plugin-syntax-typescript': 7.27.1(@babel/core@7.28.3) + '@babel/types': 7.28.2 + '@jest/expect-utils': 29.7.0 + '@jest/transform': 29.7.0 + '@jest/types': 29.6.3 + babel-preset-current-node-syntax: 1.2.0(@babel/core@7.28.3) + chalk: 4.1.2 + expect: 29.7.0 + graceful-fs: 4.2.11 + jest-diff: 29.7.0 + jest-get-type: 29.6.3 + jest-matcher-utils: 29.7.0 + jest-message-util: 29.7.0 + jest-util: 29.7.0 + natural-compare: 1.4.0 + pretty-format: 29.7.0 + semver: 7.7.3 + transitivePeerDependencies: + - supports-color + jest-snapshot@30.1.1: dependencies: '@babel/core': 7.28.3 @@ -18580,6 +19829,15 @@ snapshots: graceful-fs: 4.2.11 picomatch: 4.0.3 + jest-validate@29.7.0: + dependencies: + '@jest/types': 29.6.3 + camelcase: 6.3.0 + chalk: 4.1.2 + jest-get-type: 29.6.3 + leven: 3.1.0 + pretty-format: 29.7.0 + jest-validate@30.1.0: dependencies: '@jest/get-type': 30.1.0 @@ -18589,6 +19847,17 @@ snapshots: leven: 3.1.0 pretty-format: 30.0.5 + jest-watcher@29.7.0: + dependencies: + '@jest/test-result': 29.7.0 + '@jest/types': 29.6.3 + '@types/node': 22.19.3 + ansi-escapes: 4.3.2 + chalk: 4.1.2 + emittery: 0.13.1 + jest-util: 29.7.0 + string-length: 4.0.2 + jest-watcher@30.1.1: dependencies: '@jest/test-result': 30.1.1 @@ -18621,6 +19890,18 @@ snapshots: merge-stream: 2.0.0 supports-color: 8.1.1 + jest@29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)): + dependencies: + '@jest/core': 29.7.0(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + '@jest/types': 29.6.3 + import-local: 3.2.0 + jest-cli: 29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + transitivePeerDependencies: + - '@types/node' + - babel-plugin-macros + - supports-color + - ts-node + jest@30.1.1(@types/node@24.3.0)(ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2)): dependencies: '@jest/core': 30.1.1(ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2)) @@ -18646,6 +19927,8 @@ snapshots: '@sideway/formula': 3.0.1 '@sideway/pinpoint': 2.0.0 + js-sha256@0.11.1: {} + js-tokens@4.0.0: {} js-tokens@9.0.1: {} @@ -18840,6 +20123,8 @@ snapshots: lodash.debounce@4.0.8: {} + lodash.isequal@4.5.0: {} + lodash.memoize@4.1.2: {} lodash.merge@4.6.2: {} @@ -18926,6 +20211,12 @@ snapshots: math-intrinsics@1.1.0: {} + md5.js@1.3.5: + dependencies: + hash-base: 3.1.2 + inherits: 2.0.4 + safe-buffer: 5.2.1 + mdast-util-directive@3.1.0: dependencies: '@types/mdast': 4.0.4 @@ -20408,6 +21699,12 @@ snapshots: lodash: 4.17.21 renderkid: 3.0.0 + pretty-format@29.7.0: + dependencies: + '@jest/schemas': 29.6.3 + ansi-styles: 5.2.0 + react-is: 18.3.1 + pretty-format@30.0.5: dependencies: '@jest/schemas': 30.0.5 @@ -20458,6 +21755,8 @@ snapshots: dependencies: escape-goat: 4.0.0 + pure-rand@6.1.0: {} + pure-rand@7.0.1: {} qs@6.13.0: @@ -20826,6 +22125,8 @@ snapshots: resolve-pkg-maps@1.0.0: {} + resolve.exports@2.0.3: {} + resolve@1.22.10: dependencies: is-core-module: 2.16.1 @@ -20860,6 +22161,11 @@ snapshots: glob: 11.0.3 package-json-from-dist: 1.0.1 + ripemd160@2.0.3: + dependencies: + hash-base: 3.1.2 + inherits: 2.0.4 + rollup@4.49.0: dependencies: '@types/estree': 1.0.8 @@ -21104,6 +22410,12 @@ snapshots: setprototypeof@1.2.0: {} + sha.js@2.4.12: + dependencies: + inherits: 2.0.4 + safe-buffer: 5.2.1 + to-buffer: 1.2.2 + shallow-clone@3.0.1: dependencies: kind-of: 6.0.3 @@ -21618,6 +22930,12 @@ snapshots: tmpl@1.0.5: {} + to-buffer@1.2.2: + dependencies: + isarray: 2.0.5 + safe-buffer: 5.2.1 + typed-array-buffer: 1.0.3 + to-regex-range@5.0.1: dependencies: is-number: 7.0.0 @@ -21652,6 +22970,26 @@ snapshots: dependencies: typescript: 5.9.2 + ts-jest@29.4.1(@babel/core@7.28.3)(@jest/transform@30.1.1)(@jest/types@30.0.5)(babel-jest@30.1.1(@babel/core@7.28.3))(jest-util@30.0.5)(jest@29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)))(typescript@5.9.2): + dependencies: + bs-logger: 0.2.6 + fast-json-stable-stringify: 2.1.0 + handlebars: 4.7.8 + jest: 29.7.0(@types/node@22.19.3)(ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2)) + json5: 2.2.3 + lodash.memoize: 4.1.2 + make-error: 1.3.6 + semver: 7.7.2 + type-fest: 4.41.0 + typescript: 5.9.2 + yargs-parser: 21.1.1 + optionalDependencies: + '@babel/core': 7.28.3 + '@jest/transform': 30.1.1 + '@jest/types': 30.0.5 + babel-jest: 30.1.1(@babel/core@7.28.3) + jest-util: 30.0.5 + ts-jest@29.4.1(@babel/core@7.28.3)(@jest/transform@30.1.1)(@jest/types@30.0.5)(babel-jest@30.1.1(@babel/core@7.28.3))(jest-util@30.0.5)(jest@30.1.1(@types/node@24.3.0)(ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2)))(typescript@5.9.2): dependencies: bs-logger: 0.2.6 @@ -21682,6 +23020,25 @@ snapshots: typescript: 5.9.2 webpack: 5.100.2 + ts-node@10.9.2(@types/node@22.19.3)(typescript@5.9.2): + dependencies: + '@cspotcode/source-map-support': 0.8.1 + '@tsconfig/node10': 1.0.11 + '@tsconfig/node12': 1.0.11 + '@tsconfig/node14': 1.0.3 + '@tsconfig/node16': 1.0.4 + '@types/node': 22.19.3 + acorn: 8.15.0 + acorn-walk: 8.3.4 + arg: 4.1.3 + create-require: 1.1.1 + diff: 4.0.2 + make-error: 1.3.6 + typescript: 5.9.2 + v8-compile-cache-lib: 3.0.1 + yn: 3.1.1 + optional: true + ts-node@10.9.2(@types/node@24.3.0)(typescript@5.9.2): dependencies: '@cspotcode/source-map-support': 0.8.1 @@ -21733,6 +23090,13 @@ snapshots: optionalDependencies: fsevents: 2.3.3 + tsx@4.21.0: + dependencies: + esbuild: 0.27.2 + get-tsconfig: 4.10.1 + optionalDependencies: + fsevents: 2.3.3 + type-check@0.4.0: dependencies: prelude-ls: 1.2.1 @@ -21832,6 +23196,8 @@ snapshots: typescript: 5.9.2 yaml: 2.8.1 + typeforce@1.18.0: {} + typescript-eslint@8.41.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2): dependencies: '@typescript-eslint/eslint-plugin': 8.41.0(@typescript-eslint/parser@8.41.0(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2))(eslint@9.34.0(jiti@2.5.1))(typescript@5.9.2) @@ -21880,6 +23246,8 @@ snapshots: undici-types@6.19.8: {} + undici-types@6.21.0: {} + undici-types@7.10.0: {} unicode-canonical-property-names-ecmascript@2.0.1: {} @@ -22044,6 +23412,10 @@ snapshots: value-equal@1.0.1: {} + varuint-bitcoin@1.1.2: + dependencies: + safe-buffer: 5.2.1 + vary@1.1.2: {} vfile-location@5.0.3: @@ -22061,13 +23433,13 @@ snapshots: '@types/unist': 3.0.3 vfile-message: 4.0.3 - vite-node@3.2.4(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1): + vite-node@3.2.4(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1): dependencies: cac: 6.7.14 debug: 4.4.1 es-module-lexer: 1.7.0 pathe: 2.0.3 - vite: 7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1) + vite: 7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1) transitivePeerDependencies: - '@types/node' - jiti @@ -22082,7 +23454,7 @@ snapshots: - tsx - yaml - vite@7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1): + vite@7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1): dependencies: esbuild: 0.25.9 fdir: 6.5.0(picomatch@4.0.3) @@ -22096,14 +23468,14 @@ snapshots: jiti: 2.5.1 lightningcss: 1.30.1 terser: 5.43.1 - tsx: 4.20.5 + tsx: 4.21.0 yaml: 2.8.1 - vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1): + vitest@3.2.4(@types/debug@4.1.12)(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1): dependencies: '@types/chai': 5.2.2 '@vitest/expect': 3.2.4 - '@vitest/mocker': 3.2.4(vite@7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1)) + '@vitest/mocker': 3.2.4(vite@7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1)) '@vitest/pretty-format': 3.2.4 '@vitest/runner': 3.2.4 '@vitest/snapshot': 3.2.4 @@ -22121,8 +23493,8 @@ snapshots: tinyglobby: 0.2.14 tinypool: 1.1.1 tinyrainbow: 2.0.0 - vite: 7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1) - vite-node: 3.2.4(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.20.5)(yaml@2.8.1) + vite: 7.1.3(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1) + vite-node: 3.2.4(@types/node@24.3.0)(jiti@2.5.1)(lightningcss@1.30.1)(terser@5.43.1)(tsx@4.21.0)(yaml@2.8.1) why-is-node-running: 2.3.0 optionalDependencies: '@types/debug': 4.1.12 @@ -22388,6 +23760,10 @@ snapshots: dependencies: string-width: 5.1.2 + wif@2.0.6: + dependencies: + bs58check: 2.1.2 + wildcard@2.0.1: {} word-wrap@1.2.5: {} @@ -22421,6 +23797,11 @@ snapshots: signal-exit: 3.0.7 typedarray-to-buffer: 3.1.5 + write-file-atomic@4.0.2: + dependencies: + imurmurhash: 0.1.4 + signal-exit: 3.0.7 + write-file-atomic@5.0.1: dependencies: imurmurhash: 0.1.4 From 531e392ef44ef4fd08038bcb38fdde91b89df22e Mon Sep 17 00:00:00 2001 From: fgh Date: Tue, 30 Dec 2025 15:34:49 -0500 Subject: [PATCH 3/3] fix(rgbpp): remove duplicate @ckb-lumos deps from devDependencies and add cellDeps array null checks --- packages/rgbpp/package.json | 2 -- packages/rgbpp/src/udt/index.ts | 19 +++++++++++++------ 2 files changed, 13 insertions(+), 8 deletions(-) diff --git a/packages/rgbpp/package.json b/packages/rgbpp/package.json index 5eca043de..3d1644160 100644 --- a/packages/rgbpp/package.json +++ b/packages/rgbpp/package.json @@ -26,8 +26,6 @@ "devDependencies": { "@ckb-ccc/spore": "workspace:*", "@ckb-ccc/udt": "workspace:*", - "@ckb-lumos/base": "^0.22.2", - "@ckb-lumos/codec": "^0.22.2", "@eslint/js": "^9.34.0", "@exact-realty/multipart-parser": "^1.0.13", "@types/jest": "^29.5.14", diff --git a/packages/rgbpp/src/udt/index.ts b/packages/rgbpp/src/udt/index.ts index d03c8f94c..8c3e0ac00 100644 --- a/packages/rgbpp/src/udt/index.ts +++ b/packages/rgbpp/src/udt/index.ts @@ -125,11 +125,11 @@ export class RgbppUdtClient { } if (rgbppCells.length !== 0) { - console.log("Using existing RGB++ cell"); + // console.log("Using existing RGB++ cell"); return rgbppCells; } - console.log("RGB++ cell not found, creating a new one"); + // console.log("RGB++ cell not found, creating a new one"); const tx = ccc.Transaction.default(); // If additional capacity is required when used as an input in a transaction, it can always be supplemented in `completeInputsByCapacity`. @@ -141,7 +141,7 @@ export class RgbppUdtClient { await tx.completeFeeBy(signer); const txHash = await signer.sendTransaction(tx); await signer.client.waitTransaction(txHash); - console.log(`RGB++ cell created, txHash: ${txHash}`); + // console.log(`RGB++ cell created, txHash: ${txHash}`); const cell = await signer.client.getCellLive({ txHash, @@ -161,11 +161,11 @@ export class RgbppUdtClient { throw new Error("rgbppLiveCells is empty"); } - const rgpbbLiveCells = deduplicateByOutPoint(params.rgbppLiveCells); + const rgbppLiveCells = deduplicateByOutPoint(params.rgbppLiveCells); const tx = ccc.Transaction.default(); await Promise.all( - rgpbbLiveCells.map(async (cell) => { + rgbppLiveCells.map(async (cell) => { const cellInput = ccc.CellInput.from({ previousOutput: cell.outPoint, }); @@ -189,13 +189,20 @@ export class RgbppUdtClient { ccc.KnownScript.UniqueType, ); + if (params.udtScriptInfo.cellDeps.length === 0) { + throw new Error("udtScriptInfo.cellDeps is empty"); + } + if (uniqueTypeInfo.cellDeps.length === 0) { + throw new Error("uniqueTypeInfo.cellDeps is empty"); + } + tx.addOutput( { lock: pseudoRgbppLock, type: ccc.Script.from({ codeHash: params.udtScriptInfo.codeHash, hashType: params.udtScriptInfo.hashType, - args: params.rgbppLiveCells[0].cellOutput.lock.hash(), // unique ID of udt token + args: rgbppLiveCells[0].cellOutput.lock.hash(), // unique ID of udt token }), }, u128ToLe(params.amount * BigInt(10 ** params.token.decimal)),