@cityofzion/bs-neox 3.1.9 → 3.1.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/BSNeoX.d.ts CHANGED
@@ -1,13 +1,15 @@
1
1
  import { BSEthereum } from '@cityofzion/bs-ethereum';
2
2
  import { type TBSNetwork, type TGetLedgerTransport, type TTransactionDefault, type TTransferParams } from '@cityofzion/blockchain-service';
3
+ import { WalletConnectServiceNeoX } from './services/wallet-connect/WalletConnectServiceNeoX';
3
4
  import { Neo3NeoXBridgeService } from './services/neo3-neox-bridge/Neo3NeoXBridgeService';
4
5
  import type { IBSNeoX, TBSNeoXName, TBSNeoXNetworkId, TSendTransactionParams, TSendTransactionResponse } from './types';
5
6
  export declare class BSNeoX extends BSEthereum<TBSNeoXName, TBSNeoXNetworkId> implements IBSNeoX {
6
7
  neo3NeoXBridgeService: Neo3NeoXBridgeService;
8
+ walletConnectService: WalletConnectServiceNeoX;
7
9
  readonly defaultNetwork: TBSNetwork<TBSNeoXNetworkId>;
8
10
  readonly availableNetworks: TBSNetwork<TBSNeoXNetworkId>[];
9
11
  constructor(network?: TBSNetwork<TBSNeoXNetworkId>, getLedgerTransport?: TGetLedgerTransport<TBSNeoXName>);
10
- _sendTransaction({ signer, gasPrice, params }: TSendTransactionParams): Promise<TSendTransactionResponse>;
12
+ _sendTransaction({ signer, gasPriceBn, transactionParams, }: TSendTransactionParams): Promise<TSendTransactionResponse>;
11
13
  setNetwork(network: TBSNetwork<TBSNeoXNetworkId>): void;
12
14
  transfer({ senderAccount, intents, }: TTransferParams<TBSNeoXName>): Promise<TTransactionDefault<TBSNeoXName>[]>;
13
15
  }
package/dist/BSNeoX.js CHANGED
@@ -30,35 +30,32 @@ class BSNeoX extends bs_ethereum_1.BSEthereum {
30
30
  this.defaultNetwork = BSNeoXConstants_1.BSNeoXConstants.MAINNET_NETWORK;
31
31
  this.setNetwork(network || this.defaultNetwork);
32
32
  }
33
- async _sendTransaction({ signer, gasPrice, params }) {
33
+ async _sendTransaction({ signer, gasPriceBn, transactionParams, }) {
34
34
  const chainId = parseInt(this.network.id);
35
35
  if (isNaN(chainId)) {
36
36
  throw new Error('Invalid chainId');
37
37
  }
38
- params.chainId = chainId;
38
+ transactionParams.chainId = chainId;
39
39
  const nonce = await signer.getTransactionCount('pending');
40
40
  if (isNaN(nonce)) {
41
41
  throw new Error('Invalid nonce');
42
42
  }
43
- params.nonce = nonce;
44
- const gasParams = { maxPriorityFeePerGas: gasPrice, maxFeePerGas: gasPrice };
45
- let gasLimit;
43
+ transactionParams.nonce = nonce;
46
44
  try {
47
- gasLimit = await signer.estimateGas(params);
45
+ const estimatedGas = await signer.estimateGas(transactionParams);
46
+ transactionParams.gasLimit = new blockchain_service_1.BSBigUnitAmount(estimatedGas.toString(), bs_ethereum_1.BSEthereumConstants.DEFAULT_DECIMALS).toString();
48
47
  }
49
48
  catch {
50
- gasLimit = bs_ethereum_1.BSEthereumConstants.DEFAULT_GAS_LIMIT;
49
+ transactionParams.gasLimit = bs_ethereum_1.BSEthereumConstants.DEFAULT_GAS_LIMIT_BN.toString();
51
50
  }
52
- const fee = ethers_1.ethers.utils.formatEther(gasPrice.mul(gasLimit));
53
- const [firstTransactionResponse, firstTransactionError] = await blockchain_service_1.BSUtilsHelper.tryCatch(() => signer.sendTransaction({
54
- ...params,
55
- ...gasParams,
56
- gasLimit,
57
- }));
51
+ transactionParams.maxPriorityFeePerGas = gasPriceBn.toString();
52
+ transactionParams.maxFeePerGas = gasPriceBn.toString();
53
+ const [firstTransactionResponse, firstTransactionError] = await blockchain_service_1.BSUtilsHelper.tryCatch(() => signer.sendTransaction(transactionParams));
58
54
  const isAntiMevNetwork = BSNeoXConstants_1.BSNeoXConstants.ANTI_MEV_RPC_LIST_BY_NETWORK_ID[this.network.id].some(url => url === this.network.url);
59
55
  if (!isAntiMevNetwork) {
60
56
  if (firstTransactionError)
61
57
  throw firstTransactionError;
58
+ const fee = gasPriceBn.multipliedBy(transactionParams.gasLimit).toHuman().toFormatted();
62
59
  return { transactionHash: firstTransactionResponse.hash, fee };
63
60
  }
64
61
  if (!firstTransactionError?.error || firstTransactionError.error.message !== 'transaction cached') {
@@ -75,16 +72,18 @@ class BSNeoX extends bs_ethereum_1.BSEthereum {
75
72
  });
76
73
  const cachedTransaction = cachedTransactionResponse.data.result;
77
74
  const consensusContract = new ethers_1.ethers.Contract(BSNeoXConstants_1.BSNeoXConstants.CONSENSUS_SCRIPT_HASH, consensus_1.CONSENSUS_ABI, signer);
78
- const consensusSize = BigInt(await consensusContract.consensusSize());
75
+ const consensusSize = await consensusContract.consensusSize();
76
+ const consensusSizeBigInt = new blockchain_service_1.BSBigNumber(consensusSize.toString()).toBigInt();
79
77
  const keyManagementContract = new ethers_1.ethers.Contract(BSNeoXConstants_1.BSNeoXConstants.KEY_MANAGEMENT_SCRIPT_HASH, key_management_1.KEY_MANAGEMENT_ABI, signer);
80
- const roundNumber = BigInt(await keyManagementContract.roundNumber());
81
- const aggregatedCommitment = await keyManagementContract.aggregatedCommitments(roundNumber);
82
- const publicKey = neox_tpke_1.PublicKey.fromAggregatedCommitment((0, viem_1.toBytes)(aggregatedCommitment), (0, neox_tpke_1.getScaler)(consensusSize, (0, neox_tpke_1.getConsensusThreshold)(consensusSize)));
78
+ const roundedNumber = await keyManagementContract.roundNumber();
79
+ const roundNumberBigInt = new blockchain_service_1.BSBigNumber(roundedNumber.toString()).toBigInt();
80
+ const aggregatedCommitment = await keyManagementContract.aggregatedCommitments(roundNumberBigInt);
81
+ const publicKey = neox_tpke_1.PublicKey.fromAggregatedCommitment((0, viem_1.toBytes)(aggregatedCommitment), (0, neox_tpke_1.getScaler)(consensusSizeBigInt, (0, neox_tpke_1.getConsensusThreshold)(consensusSizeBigInt)));
83
82
  const { encryptedKey, encryptedMsg } = publicKey.encrypt((0, viem_1.toBytes)(cachedTransaction));
84
83
  const parsedTransaction = (0, viem_1.parseTransaction)(cachedTransaction);
85
84
  const envelopedData = (0, viem_1.concat)([
86
85
  new Uint8Array([0xff, 0xff, 0xff, 0xff]),
87
- (0, viem_1.pad)((0, viem_1.toBytes)(roundNumber), { size: 4 }),
86
+ (0, viem_1.pad)((0, viem_1.toBytes)(roundNumberBigInt), { size: 4 }),
88
87
  (0, viem_1.pad)((0, viem_1.toBytes)(parsedTransaction.gas), { size: 4 }),
89
88
  (0, viem_1.toBytes)((0, viem_1.keccak256)(cachedTransaction)),
90
89
  encryptedKey,
@@ -97,19 +96,19 @@ class BSNeoX extends bs_ethereum_1.BSEthereum {
97
96
  data: (0, viem_1.toHex)(envelopedData),
98
97
  };
99
98
  try {
100
- gasLimit = await signer.estimateGas(newParams);
99
+ const estimatedGas = await signer.estimateGas(newParams);
100
+ newParams.gasLimit = new blockchain_service_1.BSBigUnitAmount(estimatedGas.toString(), bs_ethereum_1.BSEthereumConstants.DEFAULT_DECIMALS).toString();
101
101
  }
102
102
  catch {
103
- gasLimit = bs_ethereum_1.BSEthereumConstants.DEFAULT_GAS_LIMIT;
103
+ newParams.gasLimit = bs_ethereum_1.BSEthereumConstants.DEFAULT_GAS_LIMIT_BN.toString();
104
104
  }
105
- const [secondTransactionResponse, secondTransactionError] = await blockchain_service_1.BSUtilsHelper.tryCatch(() => signer.sendTransaction({
106
- ...newParams,
107
- ...gasParams,
108
- gasLimit,
109
- }));
105
+ newParams.maxPriorityFeePerGas = gasPriceBn.toString();
106
+ newParams.maxFeePerGas = gasPriceBn.toString();
107
+ const [secondTransactionResponse, secondTransactionError] = await blockchain_service_1.BSUtilsHelper.tryCatch(() => signer.sendTransaction(newParams));
110
108
  const transactionHash = secondTransactionResponse?.hash || secondTransactionError?.returnedHash;
111
109
  if (!transactionHash)
112
110
  throw secondTransactionError || new Error('Transaction error');
111
+ const fee = gasPriceBn.multipliedBy(newParams.gasLimit).toHuman().toFormatted();
113
112
  return { transactionHash, fee };
114
113
  }
115
114
  setNetwork(network) {
@@ -138,8 +137,8 @@ class BSNeoX extends bs_ethereum_1.BSEthereum {
138
137
  let error;
139
138
  for (const intent of intents) {
140
139
  try {
141
- const { transactionParams, gasPrice } = await this._buildTransferParams(intent);
142
- const { transactionHash, fee } = await this._sendTransaction({ signer, gasPrice, params: transactionParams });
140
+ const { transactionParams, gasPriceBn } = await this._buildTransferParams(intent);
141
+ const { transactionHash, fee } = await this._sendTransaction({ signer, gasPriceBn, transactionParams });
143
142
  if (transactionHash) {
144
143
  const { receiverAddress, token } = intent;
145
144
  const tokenHash = token.hash;
@@ -23,7 +23,11 @@ BSNeoXConstants.RPC_LIST_BY_NETWORK_ID = {
23
23
  'https://mainnet-2.rpc.banelabs.org',
24
24
  'https://mainnet-3.rpc.banelabs.org',
25
25
  ],
26
- '12227332': [..._a.ANTI_MEV_RPC_LIST_BY_NETWORK_ID['12227332'], 'https://testnet.rpc.banelabs.org'],
26
+ '12227332': [
27
+ ..._a.ANTI_MEV_RPC_LIST_BY_NETWORK_ID['12227332'],
28
+ 'https://neoxt4seed2.ngd.network',
29
+ 'https://neoxt4seed3.ngd.network',
30
+ ],
27
31
  };
28
32
  BSNeoXConstants.MAINNET_NETWORK = {
29
33
  id: '47763',
@@ -43,9 +43,7 @@ class BlockscoutBDSNeoX extends bs_ethereum_1.RpcBDSEthereum {
43
43
  const toUrl = this._service.explorerService.buildAddressUrl(to);
44
44
  events.splice(0, 0, {
45
45
  eventType: 'token',
46
- amount: blockchain_service_1.BSBigNumberHelper.format(blockchain_service_1.BSBigNumberHelper.fromDecimals(response.value, nativeToken.decimals), {
47
- decimals: nativeToken.decimals,
48
- }),
46
+ amount: new blockchain_service_1.BSBigUnitAmount(response.value, nativeToken.decimals).toHuman().toFormatted(),
49
47
  methodName: 'transfer',
50
48
  from,
51
49
  fromUrl,
@@ -73,9 +71,9 @@ class BlockscoutBDSNeoX extends bs_ethereum_1.RpcBDSEthereum {
73
71
  });
74
72
  events.splice(index, 0, {
75
73
  eventType: 'token',
76
- amount: blockchain_service_1.BSBigNumberHelper.format(blockchain_service_1.BSBigNumberHelper.fromDecimals(tokenTransfer.total.value, tokenTransfer.total.decimals), {
77
- decimals: tokenTransfer.total.decimals,
78
- }),
74
+ amount: new blockchain_service_1.BSBigUnitAmount(tokenTransfer.total.value, tokenTransfer.total.decimals)
75
+ .toHuman()
76
+ .toFormatted(),
79
77
  methodName: 'transfer',
80
78
  from,
81
79
  fromUrl,
@@ -112,9 +110,9 @@ class BlockscoutBDSNeoX extends bs_ethereum_1.RpcBDSEthereum {
112
110
  txIdUrl: this._service.explorerService.buildTransactionUrl(txId),
113
111
  block: response.block,
114
112
  date: new Date(response.timestamp).toJSON(),
115
- networkFeeAmount: blockchain_service_1.BSBigNumberHelper.format(blockchain_service_1.BSBigNumberHelper.fromDecimals(response.fee.value, this._service.feeToken.decimals), {
116
- decimals: this._service.feeToken.decimals,
117
- }),
113
+ networkFeeAmount: new blockchain_service_1.BSBigUnitAmount(response.fee.value, this._service.feeToken.decimals)
114
+ .toHuman()
115
+ .toFormatted(),
118
116
  view: 'default',
119
117
  events,
120
118
  data,
@@ -142,9 +140,7 @@ class BlockscoutBDSNeoX extends bs_ethereum_1.RpcBDSEthereum {
142
140
  const toUrl = this._service.explorerService.buildAddressUrl(to);
143
141
  events.push({
144
142
  eventType: 'token',
145
- amount: blockchain_service_1.BSBigNumberHelper.format(blockchain_service_1.BSBigNumberHelper.fromDecimals(item.value, nativeToken.decimals), {
146
- decimals: nativeToken.decimals,
147
- }),
143
+ amount: new blockchain_service_1.BSBigUnitAmount(item.value, nativeToken.decimals).toHuman().toFormatted(),
148
144
  methodName: 'transfer',
149
145
  from,
150
146
  fromUrl,
@@ -170,9 +166,7 @@ class BlockscoutBDSNeoX extends bs_ethereum_1.RpcBDSEthereum {
170
166
  const value = result[1];
171
167
  events.push({
172
168
  eventType: 'token',
173
- amount: blockchain_service_1.BSBigNumberHelper.format(blockchain_service_1.BSBigNumberHelper.fromDecimals(value, token.decimals), {
174
- decimals: token.decimals,
175
- }),
169
+ amount: new blockchain_service_1.BSBigUnitAmount(value, token.decimals).toHuman().toFormatted(),
176
170
  methodName: 'transfer',
177
171
  from,
178
172
  fromUrl,
@@ -199,9 +193,7 @@ class BlockscoutBDSNeoX extends bs_ethereum_1.RpcBDSEthereum {
199
193
  txIdUrl: this._service.explorerService.buildTransactionUrl(txId),
200
194
  block: item.block,
201
195
  date: new Date(item.timestamp).toJSON(),
202
- networkFeeAmount: blockchain_service_1.BSBigNumberHelper.format(blockchain_service_1.BSBigNumberHelper.fromDecimals(item.fee.value, this._service.feeToken.decimals), {
203
- decimals: this._service.feeToken.decimals,
204
- }),
196
+ networkFeeAmount: new blockchain_service_1.BSBigUnitAmount(item.fee.value, this._service.feeToken.decimals).toHuman().toFormatted(),
205
197
  view: 'default',
206
198
  events,
207
199
  data,
@@ -274,9 +266,7 @@ class BlockscoutBDSNeoX extends bs_ethereum_1.RpcBDSEthereum {
274
266
  const nativeToken = BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET;
275
267
  const balances = [
276
268
  {
277
- amount: blockchain_service_1.BSBigNumberHelper.format(blockchain_service_1.BSBigNumberHelper.fromDecimals(nativeBalance.coin_balance, nativeToken.decimals), {
278
- decimals: nativeToken.decimals,
279
- }),
269
+ amount: new blockchain_service_1.BSBigUnitAmount(nativeBalance.coin_balance, nativeToken.decimals).toHuman().toFormatted(),
280
270
  token: nativeToken,
281
271
  },
282
272
  ];
@@ -296,9 +286,7 @@ class BlockscoutBDSNeoX extends bs_ethereum_1.RpcBDSEthereum {
296
286
  symbol: balance.token.symbol,
297
287
  });
298
288
  balances.push({
299
- amount: blockchain_service_1.BSBigNumberHelper.format(blockchain_service_1.BSBigNumberHelper.fromDecimals(balance.value, token.decimals), {
300
- decimals: token.decimals,
301
- }),
289
+ amount: new blockchain_service_1.BSBigUnitAmount(balance.value, token.decimals).toHuman().toFormatted(),
302
290
  token,
303
291
  });
304
292
  }
@@ -49,7 +49,7 @@ class BlockscoutFullTransactionsDataService {
49
49
  block: item.block,
50
50
  date: item.date,
51
51
  networkFeeAmount: networkFeeAmount
52
- ? blockchain_service_1.BSBigNumberHelper.format(networkFeeAmount, { decimals: BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET.decimals })
52
+ ? new blockchain_service_1.BSBigHumanAmount(networkFeeAmount, BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET.decimals).toFormatted()
53
53
  : undefined,
54
54
  view: 'default',
55
55
  events: [],
@@ -82,7 +82,7 @@ class BlockscoutFullTransactionsDataService {
82
82
  newItem.events.splice(eventIndex, 0, {
83
83
  eventType: 'token',
84
84
  amount: event.amount
85
- ? blockchain_service_1.BSBigNumberHelper.format(event.amount, { decimals: token?.decimals ?? event.tokenDecimals })
85
+ ? new blockchain_service_1.BSBigHumanAmount(event.amount, token?.decimals ?? event.tokenDecimals).toFormatted()
86
86
  : undefined,
87
87
  methodName,
88
88
  from,
@@ -102,7 +102,7 @@ class BlockscoutFullTransactionsDataService {
102
102
  ...newItem,
103
103
  data: {
104
104
  neo3NeoxBridge: {
105
- amount: blockchain_service_1.BSBigNumberHelper.format(bridgeData.amount, { decimals: tokenToUse.decimals }),
105
+ amount: new blockchain_service_1.BSBigHumanAmount(bridgeData.amount, tokenToUse.decimals).toFormatted(),
106
106
  tokenToUse,
107
107
  receiverAddress: bridgeData.receiverBridgeAddress,
108
108
  },
@@ -44,24 +44,21 @@ class Neo3NeoXBridgeService {
44
44
  const to = input.args._to;
45
45
  const receiverAddress = wallet.getAddressFromScriptHash(to.startsWith('0x') ? to.slice(2) : to);
46
46
  let tokenToUse;
47
- let amountBn;
47
+ let amount;
48
48
  if (input.name === 'withdrawNative') {
49
49
  tokenToUse = this.gasToken;
50
- amountBn = blockchain_service_1.BSBigNumberHelper.fromDecimals(response.value, tokenToUse.decimals).minus(_a.BRIDGE_FEE);
50
+ amount = new blockchain_service_1.BSBigUnitAmount(response.value, tokenToUse.decimals)
51
+ .toHuman()
52
+ .minus(_a.BRIDGE_FEE)
53
+ .toFormatted();
51
54
  }
52
55
  else if (input.name === 'withdrawToken') {
53
56
  tokenToUse = this.neoToken;
54
- amountBn = blockchain_service_1.BSBigNumberHelper.fromDecimals(input.args._amount.toString(), tokenToUse.decimals);
57
+ amount = new blockchain_service_1.BSBigUnitAmount(input.args._amount.toString(), tokenToUse.decimals).toHuman().toFormatted();
55
58
  }
56
- if (!tokenToUse || !amountBn)
59
+ if (!tokenToUse || !amount)
57
60
  return undefined;
58
- return {
59
- neo3NeoxBridge: {
60
- tokenToUse,
61
- receiverAddress,
62
- amount: blockchain_service_1.BSBigNumberHelper.format(amountBn, { decimals: tokenToUse.decimals }),
63
- },
64
- };
61
+ return { neo3NeoxBridge: { tokenToUse, receiverAddress, amount } };
65
62
  }
66
63
  async getBridgeConstants(token) {
67
64
  try {
@@ -71,12 +68,15 @@ class Neo3NeoXBridgeService {
71
68
  const response = isNativeToken
72
69
  ? await bridgeContract.nativeBridge()
73
70
  : await bridgeContract.tokenBridges(token.hash);
74
- const bridgeFeeBn = blockchain_service_1.BSBigNumberHelper.fromDecimals(response.config.fee.toString(), BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET.decimals);
75
- const minAmountBn = blockchain_service_1.BSBigNumberHelper.fromDecimals(response.config.minAmount.toString(), token.decimals);
76
- const maxAmountBn = blockchain_service_1.BSBigNumberHelper.fromDecimals(response.config.maxAmount.toString(), token.decimals);
77
- const bridgeFee = blockchain_service_1.BSBigNumberHelper.format(bridgeFeeBn, { decimals: BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET.decimals });
78
- const bridgeMinAmount = blockchain_service_1.BSBigNumberHelper.format(minAmountBn, { decimals: token.decimals });
79
- const bridgeMaxAmount = blockchain_service_1.BSBigNumberHelper.format(maxAmountBn, { decimals: token.decimals });
71
+ const bridgeFee = new blockchain_service_1.BSBigUnitAmount(response.config.fee.toString(), BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET.decimals)
72
+ .toHuman()
73
+ .toFormatted();
74
+ const bridgeMinAmount = new blockchain_service_1.BSBigUnitAmount(response.config.minAmount.toString(), token.decimals)
75
+ .toHuman()
76
+ .toFormatted();
77
+ const bridgeMaxAmount = new blockchain_service_1.BSBigUnitAmount(response.config.maxAmount.toString(), token.decimals)
78
+ .toHuman()
79
+ .toFormatted();
80
80
  return {
81
81
  bridgeFee,
82
82
  bridgeMaxAmount,
@@ -109,7 +109,10 @@ class Neo3NeoXBridgeService {
109
109
  const approvedEstimated = await signer.estimateGas({ ...populatedApproveTransaction, chainId, nonce, type: 2 });
110
110
  const provider = new ethers_1.ethers.providers.JsonRpcProvider(__classPrivateFieldGet(this, _Neo3NeoXBridgeService_service, "f").network.url);
111
111
  const gasPrice = await provider.getGasPrice();
112
- return ethers_1.ethers.utils.formatEther(gasPrice.mul(approvedEstimated));
112
+ return new blockchain_service_1.BSBigUnitAmount(gasPrice.toString(), bs_ethereum_1.BSEthereumConstants.DEFAULT_DECIMALS)
113
+ .multipliedBy(approvedEstimated.toString())
114
+ .toHuman()
115
+ .toFormatted();
113
116
  }
114
117
  catch (error) {
115
118
  if (error instanceof blockchain_service_1.BSError) {
@@ -126,33 +129,33 @@ class Neo3NeoXBridgeService {
126
129
  const bridgeContract = new ethers_1.ethers.Contract(_a.BRIDGE_SCRIPT_HASH, bridge_1.BRIDGE_ABI);
127
130
  const { wallet } = bs_neo3_1.BSNeo3NeonJsSingletonHelper.getInstance();
128
131
  const to = `0x${wallet.getScriptHashFromAddress(params.receiverAddress)}`;
129
- const bridgeFee = ethers_1.ethers.utils.parseUnits(params.bridgeFee, BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET.decimals);
132
+ const bridgeFee = new blockchain_service_1.BSBigHumanAmount(params.bridgeFee, BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET.decimals).toUnit().toString();
130
133
  const isNativeToken = __classPrivateFieldGet(this, _Neo3NeoXBridgeService_service, "f").tokenService.predicateByHash(params.token, BSNeoXConstants_1.BSNeoXConstants.NATIVE_ASSET);
131
134
  const gasPrice = await signer.getGasPrice();
135
+ const gasPriceBn = new blockchain_service_1.BSBigUnitAmount(gasPrice.toString(), bs_ethereum_1.BSEthereumConstants.DEFAULT_DECIMALS);
132
136
  const transactionParams = { type: 2 };
133
137
  if (isNativeToken) {
134
138
  const populatedTransactionParams = await bridgeContract.populateTransaction.withdrawNative(to, bridgeFee);
135
- Object.assign(transactionParams, populatedTransactionParams, {
136
- value: ethers_1.ethers.utils.parseUnits(params.amount, params.token.decimals).add(bridgeFee),
137
- });
139
+ const value = new blockchain_service_1.BSBigHumanAmount(params.amount, params.token.decimals).toUnit().plus(bridgeFee).toString();
140
+ Object.assign(transactionParams, populatedTransactionParams, { value });
138
141
  }
139
142
  else {
140
143
  const approveTransactionParam = await __classPrivateFieldGet(this, _Neo3NeoXBridgeService_instances, "m", _Neo3NeoXBridgeService_buildApproveTransactionParam).call(this, params);
141
144
  if (approveTransactionParam) {
142
145
  const { transactionHash } = await __classPrivateFieldGet(this, _Neo3NeoXBridgeService_service, "f")._sendTransaction({
143
146
  signer,
144
- gasPrice,
145
- params: approveTransactionParam,
147
+ gasPriceBn,
148
+ transactionParams: approveTransactionParam,
146
149
  });
147
150
  const provider = new ethers_1.ethers.providers.JsonRpcProvider(__classPrivateFieldGet(this, _Neo3NeoXBridgeService_service, "f").network.url);
148
151
  await provider.waitForTransaction(transactionHash);
149
152
  }
150
- const fixedAmount = blockchain_service_1.BSBigNumberHelper.format(params.amount, { decimals: 0 });
151
- const amount = ethers_1.ethers.utils.parseUnits(fixedAmount, params.token.decimals);
153
+ const fixedAmount = new blockchain_service_1.BSBigHumanAmount(params.amount, 0).toFormatted();
154
+ const amount = new blockchain_service_1.BSBigHumanAmount(fixedAmount, params.token.decimals).toUnit().toString();
152
155
  const populatedTransactionParams = await bridgeContract.populateTransaction.withdrawToken(params.token.hash, to, amount);
153
156
  Object.assign(transactionParams, populatedTransactionParams, { value: bridgeFee });
154
157
  }
155
- const { transactionHash } = await __classPrivateFieldGet(this, _Neo3NeoXBridgeService_service, "f")._sendTransaction({ signer, gasPrice, params: transactionParams });
158
+ const { transactionHash } = await __classPrivateFieldGet(this, _Neo3NeoXBridgeService_service, "f")._sendTransaction({ signer, gasPriceBn, transactionParams });
156
159
  return transactionHash;
157
160
  }
158
161
  async getNonce(params) {
@@ -211,13 +214,13 @@ _a = Neo3NeoXBridgeService, _Neo3NeoXBridgeService_service = new WeakMap(), _Neo
211
214
  const provider = new ethers_1.ethers.providers.JsonRpcProvider(__classPrivateFieldGet(this, _Neo3NeoXBridgeService_service, "f").network.url);
212
215
  const erc20Contract = new ethers_1.ethers.Contract(params.token.hash, bs_ethereum_1.ERC20_ABI, provider);
213
216
  const allowance = await erc20Contract.allowance(params.account.address, _a.BRIDGE_SCRIPT_HASH);
214
- const allowanceNumber = blockchain_service_1.BSBigNumberHelper.fromDecimals(allowance.toString(), this.neoToken.decimals);
217
+ const allowanceNumber = new blockchain_service_1.BSBigUnitAmount(allowance.toString(), this.neoToken.decimals);
215
218
  // We are using 0 as the decimals because the NEO token in Neo3 has 0 decimals
216
- const fixedAmount = blockchain_service_1.BSBigNumberHelper.format(params.amount, { decimals: 0 });
217
- if (allowanceNumber.isGreaterThanOrEqualTo(fixedAmount)) {
219
+ const fixedAmount = new blockchain_service_1.BSBigHumanAmount(params.amount, 0).toFormatted();
220
+ const amount = new blockchain_service_1.BSBigHumanAmount(fixedAmount, params.token.decimals).toUnit().toString();
221
+ if (allowanceNumber.isGreaterThanOrEqualTo(amount)) {
218
222
  return null;
219
223
  }
220
- const amount = ethers_1.ethers.utils.parseUnits(fixedAmount, params.token.decimals);
221
224
  return await erc20Contract.populateTransaction.approve(_a.BRIDGE_SCRIPT_HASH, amount);
222
225
  };
223
226
  Neo3NeoXBridgeService.BRIDGE_SCRIPT_HASH = '0x1212000000000000000000000000000000000004';
@@ -1,7 +1,8 @@
1
- import { GhostMarketNDSEthereum } from '@cityofzion/bs-ethereum';
1
+ import { GhostMarketNDS, type THasTokenParams } from '@cityofzion/blockchain-service';
2
2
  import type { IBSNeoX, TBSNeoXName, TBSNeoXNetworkId } from '../../types';
3
- export declare class GhostMarketNDSNeoX extends GhostMarketNDSEthereum<TBSNeoXName, TBSNeoXNetworkId> {
3
+ export declare class GhostMarketNDSNeoX extends GhostMarketNDS<TBSNeoXName, TBSNeoXNetworkId, IBSNeoX> {
4
4
  static readonly CHAIN_BY_NETWORK_ID: Partial<Record<TBSNeoXNetworkId, string>>;
5
5
  constructor(service: IBSNeoX);
6
+ hasToken({ address, collectionHash }: THasTokenParams): Promise<boolean>;
6
7
  getChain(): string;
7
8
  }
@@ -2,10 +2,27 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.GhostMarketNDSNeoX = void 0;
4
4
  const bs_ethereum_1 = require("@cityofzion/bs-ethereum");
5
- class GhostMarketNDSNeoX extends bs_ethereum_1.GhostMarketNDSEthereum {
5
+ const blockchain_service_1 = require("@cityofzion/blockchain-service");
6
+ const ethers_1 = require("ethers");
7
+ class GhostMarketNDSNeoX extends blockchain_service_1.GhostMarketNDS {
6
8
  constructor(service) {
7
9
  super(service);
8
10
  }
11
+ async hasToken({ address, collectionHash }) {
12
+ try {
13
+ if (!collectionHash)
14
+ return false;
15
+ const provider = new ethers_1.ethers.providers.JsonRpcProvider(this._service.network.url);
16
+ const contract = new ethers_1.ethers.Contract(collectionHash, bs_ethereum_1.ERC20_ABI, provider);
17
+ const response = await contract.balanceOf(address);
18
+ if (!response)
19
+ return false;
20
+ return new blockchain_service_1.BSBigUnitAmount(response.toString(), 0).isGreaterThan(0);
21
+ }
22
+ catch {
23
+ return false;
24
+ }
25
+ }
9
26
  getChain() {
10
27
  const chain = GhostMarketNDSNeoX.CHAIN_BY_NETWORK_ID[this._service.network.id];
11
28
  if (!chain)
@@ -1,9 +1,13 @@
1
- import { type TWalletConnectServiceRequestMethodParams, type THexString } from '@cityofzion/blockchain-service';
2
- import { WalletConnectServiceEthereum } from '@cityofzion/bs-ethereum';
3
- import type { IBSNeoX, TBSNeoXName, TBSNeoXNetworkId } from '../../types';
4
- export declare class WalletConnectServiceNeoX extends WalletConnectServiceEthereum<TBSNeoXName, TBSNeoXNetworkId> {
1
+ import { type TWalletConnectEthereumHandlers, WalletConnectServiceEthereum } from '@cityofzion/bs-ethereum';
2
+ import type { IBSNeoX, TBSNeoXName, TBSNeoXNetworkId, TWalletConnectServiceNeoxMethod } from '../../types';
3
+ import z from 'zod';
4
+ declare const getCachedTransactionParamsSchema: z.ZodTuple<[z.ZodString, z.ZodString], null>;
5
+ type TWalletConnectNeoXHandlers = TWalletConnectEthereumHandlers & {
6
+ eth_getTransactionCount: unknown;
7
+ eth_getCachedTransaction: z.infer<typeof getCachedTransactionParamsSchema>;
8
+ };
9
+ export declare class WalletConnectServiceNeoX extends WalletConnectServiceEthereum<TBSNeoXName, TBSNeoXNetworkId, TWalletConnectServiceNeoxMethod, TWalletConnectNeoXHandlers> {
10
+ #private;
5
11
  constructor(service: IBSNeoX);
6
- eth_getTransactionCount(args: TWalletConnectServiceRequestMethodParams<TBSNeoXName>): Promise<number>;
7
- eth_getCachedTransaction(args: TWalletConnectServiceRequestMethodParams<TBSNeoXName>): Promise<THexString>;
8
- eth_sendTransaction(args: TWalletConnectServiceRequestMethodParams<TBSNeoXName>): Promise<string>;
9
12
  }
13
+ export {};
@@ -1,7 +1,13 @@
1
1
  "use strict";
2
+ var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
3
+ if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
4
+ if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
5
+ return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
6
+ };
2
7
  var __importDefault = (this && this.__importDefault) || function (mod) {
3
8
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
9
  };
10
+ var _WalletConnectServiceNeoX_getTransactionCountHandler, _WalletConnectServiceNeoX_getCachedTransactionHandler, _WalletConnectServiceNeoX_sendTransactionHandler;
5
11
  Object.defineProperty(exports, "__esModule", { value: true });
6
12
  exports.WalletConnectServiceNeoX = void 0;
7
13
  const blockchain_service_1 = require("@cityofzion/blockchain-service");
@@ -9,42 +15,61 @@ const ethers_1 = require("ethers");
9
15
  const bs_ethereum_1 = require("@cityofzion/bs-ethereum");
10
16
  const viem_1 = require("viem");
11
17
  const axios_1 = __importDefault(require("axios"));
18
+ const zod_1 = __importDefault(require("zod"));
19
+ const getCachedTransactionParamsSchema = zod_1.default.tuple([zod_1.default.string(), zod_1.default.string()]);
12
20
  class WalletConnectServiceNeoX extends bs_ethereum_1.WalletConnectServiceEthereum {
13
21
  constructor(service) {
14
22
  super(service);
15
- this.supportedMethods.push('eth_getTransactionCount', 'eth_getCachedTransaction');
16
- }
17
- async eth_getTransactionCount(args) {
18
- const wallet = await this._service._generateSigner(args.account);
19
- const provider = new ethers_1.ethers.providers.JsonRpcProvider(this._service.network.url);
20
- const connectedWallet = wallet.connect(provider);
21
- return await connectedWallet.getTransactionCount('pending');
22
- }
23
- async eth_getCachedTransaction(args) {
24
- const url = this._service.network.url;
25
- const wallet = await this._service._generateSigner(args.account);
26
- const provider = new ethers_1.ethers.providers.JsonRpcProvider(url);
27
- const connectedWallet = wallet.connect(provider);
28
- const nonce = args.params[0];
29
- const signature = await connectedWallet.signMessage(nonce.toString());
30
- const hexNonce = (0, viem_1.toHex)(nonce);
31
- // Keep using Axios because of the wallet, provider and connectedWallet don't have the eth_getCachedTransaction method
32
- const cachedTransactionResponse = await axios_1.default.post(url, {
33
- id: Date.now(),
34
- jsonrpc: '2.0',
35
- method: 'eth_getCachedTransaction',
36
- params: [hexNonce, signature],
23
+ _WalletConnectServiceNeoX_getTransactionCountHandler.set(this, {
24
+ validate: async () => { },
25
+ process: async (args) => {
26
+ const wallet = await this._service._generateSigner(args.account);
27
+ const provider = new ethers_1.ethers.providers.JsonRpcProvider(this._service.network.url);
28
+ const connectedWallet = wallet.connect(provider);
29
+ return await connectedWallet.getTransactionCount('pending');
30
+ },
37
31
  });
38
- return cachedTransactionResponse.data.result;
39
- }
40
- async eth_sendTransaction(args) {
41
- const { wallet, provider, param } = await this._resolveParams(args);
42
- const connectedWallet = wallet.connect(provider);
43
- const [response, error] = await blockchain_service_1.BSUtilsHelper.tryCatch(() => connectedWallet.sendTransaction(param));
44
- const transactionHash = response?.hash || error?.returnedHash;
45
- if (!transactionHash)
46
- throw error || new Error('Transaction error');
47
- return transactionHash;
32
+ _WalletConnectServiceNeoX_getCachedTransactionHandler.set(this, {
33
+ validate: async (params) => await getCachedTransactionParamsSchema.parseAsync(params),
34
+ process: async (args) => {
35
+ const url = this._service.network.url;
36
+ const wallet = await this._service._generateSigner(args.account);
37
+ const provider = new ethers_1.ethers.providers.JsonRpcProvider(url);
38
+ const connectedWallet = wallet.connect(provider);
39
+ const nonce = args.params[0];
40
+ const signature = await connectedWallet.signMessage(nonce.toString());
41
+ const hexNonce = (0, viem_1.toHex)(nonce);
42
+ // Keep using Axios because of the wallet, provider and connectedWallet don't have the eth_getCachedTransaction method
43
+ const cachedTransactionResponse = await axios_1.default.post(url, {
44
+ id: Date.now(),
45
+ jsonrpc: '2.0',
46
+ method: 'eth_getCachedTransaction',
47
+ params: [hexNonce, signature],
48
+ });
49
+ return cachedTransactionResponse.data.result;
50
+ },
51
+ });
52
+ _WalletConnectServiceNeoX_sendTransactionHandler.set(this, {
53
+ validate: async (params) => await this._sendTransactionHandler.validate(params),
54
+ process: async (args) => {
55
+ const { transaction, connectedWallet } = await this._resolveTransactionParams(args);
56
+ const [response, error] = await blockchain_service_1.BSUtilsHelper.tryCatch(() => connectedWallet.sendTransaction(transaction));
57
+ const transactionHash = response?.hash || error?.returnedHash;
58
+ if (!transactionHash) {
59
+ throw error || new blockchain_service_1.BSError('Transaction error', 'TRANSACTION_ERROR');
60
+ }
61
+ return transactionHash;
62
+ },
63
+ });
64
+ this.supportedMethods.push('eth_getTransactionCount', 'eth_getCachedTransaction');
65
+ this.autoApproveMethods.push('eth_getTransactionCount', 'eth_getCachedTransaction');
66
+ this.handlers = {
67
+ ...this.handlers,
68
+ eth_getTransactionCount: __classPrivateFieldGet(this, _WalletConnectServiceNeoX_getTransactionCountHandler, "f"),
69
+ eth_getCachedTransaction: __classPrivateFieldGet(this, _WalletConnectServiceNeoX_getCachedTransactionHandler, "f"),
70
+ eth_sendTransaction: __classPrivateFieldGet(this, _WalletConnectServiceNeoX_sendTransactionHandler, "f"),
71
+ };
48
72
  }
49
73
  }
50
74
  exports.WalletConnectServiceNeoX = WalletConnectServiceNeoX;
75
+ _WalletConnectServiceNeoX_getTransactionCountHandler = new WeakMap(), _WalletConnectServiceNeoX_getCachedTransactionHandler = new WeakMap(), _WalletConnectServiceNeoX_sendTransactionHandler = new WeakMap();
package/dist/types.d.ts CHANGED
@@ -1,5 +1,5 @@
1
- import type { IBSWithNeo3NeoXBridge, TBSNetworkId } from '@cityofzion/blockchain-service';
2
- import { ERC20_ABI, IBSEthereum } from '@cityofzion/bs-ethereum';
1
+ import type { BSBigUnitAmount, IBSWithNeo3NeoXBridge, TBSNetworkId } from '@cityofzion/blockchain-service';
2
+ import { ERC20_ABI, IBSEthereum, type TWalletConnectServiceEthereumMethod } from '@cityofzion/bs-ethereum';
3
3
  import { ethers, Signer } from 'ethers';
4
4
  import type { Neo3NeoXBridgeService } from './services/neo3-neox-bridge/Neo3NeoXBridgeService';
5
5
  export type TBSNeoXNetworkId = TBSNetworkId<'47763' | '12227332'>;
@@ -93,10 +93,11 @@ export type TNeo3NeoXBridgeServiceGetTransactionByNonceApiReponse = {
93
93
  };
94
94
  export type TSendTransactionParams = {
95
95
  signer: Signer;
96
- gasPrice: ethers.BigNumber;
97
- params: ethers.utils.Deferrable<ethers.providers.TransactionRequest>;
96
+ gasPriceBn: BSBigUnitAmount;
97
+ transactionParams: ethers.utils.Deferrable<ethers.providers.TransactionRequest>;
98
98
  };
99
99
  export type TSendTransactionResponse = {
100
100
  transactionHash: string;
101
101
  fee: string;
102
102
  };
103
+ export type TWalletConnectServiceNeoxMethod = TWalletConnectServiceEthereumMethod | 'eth_getTransactionCount' | 'eth_getCachedTransaction';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cityofzion/bs-neox",
3
- "version": "3.1.9",
3
+ "version": "3.1.11",
4
4
  "repository": "https://github.com/CityOfZion/blockchain-services",
5
5
  "license": "GPL-3.0-only",
6
6
  "author": "Coz",
@@ -11,13 +11,14 @@
11
11
  ],
12
12
  "dependencies": {
13
13
  "@cityofzion/dora-ts": "0.6.2",
14
- "axios": "~1.13.5",
14
+ "axios": "~1.15.0",
15
15
  "ethers": "~5.7.2",
16
16
  "neox-tpke": "~1.0.5",
17
17
  "viem": "~2.38.5",
18
- "@cityofzion/bs-ethereum": "3.1.9",
19
- "@cityofzion/bs-neo3": "3.1.9",
20
- "@cityofzion/blockchain-service": "3.1.9"
18
+ "zod": "~4.3.6",
19
+ "@cityofzion/blockchain-service": "3.1.11",
20
+ "@cityofzion/bs-ethereum": "3.1.11",
21
+ "@cityofzion/bs-neo3": "3.1.11"
21
22
  },
22
23
  "devDependencies": {
23
24
  "@ledgerhq/hw-transport": "~6.32.0",