From 1ac6041d4d4f8dc912037cf79f4c1f8934b1389c Mon Sep 17 00:00:00 2001 From: Hitansh Madan Date: Tue, 9 Dec 2025 15:06:25 +0530 Subject: [PATCH] fix(sdk-coin-tao): support all valid netuids for transferStake tx Ticket: WIN-8225 TICKET: WIN-8225 --- .../abstract-substrate/src/lib/txnSchema.ts | 4 +- .../src/lib/tokenTransferBuilder.ts | 12 +++++ .../src/lib/tokenTransferTransaction.ts | 24 ---------- modules/sdk-coin-tao/test/resources/index.ts | 2 +- .../tokenTransferBuilder.ts | 44 +++++++++++++------ 5 files changed, 45 insertions(+), 41 deletions(-) diff --git a/modules/abstract-substrate/src/lib/txnSchema.ts b/modules/abstract-substrate/src/lib/txnSchema.ts index 3628c2a4f0..0a20669818 100644 --- a/modules/abstract-substrate/src/lib/txnSchema.ts +++ b/modules/abstract-substrate/src/lib/txnSchema.ts @@ -61,8 +61,8 @@ export const UnstakeTransactionSchema = joi.object({ export const TransferStakeTransactionSchema = joi.object({ destinationColdkey: addressSchema.required(), hotkey: addressSchema.required(), - originNetuid: joi.string().required(), - destinationNetuid: joi.string().required(), + originNetuid: joi.string().regex(/^\d+$/).required(), + destinationNetuid: joi.string().regex(/^\d+$/).required(), alphaAmount: joi.string().required(), }); diff --git a/modules/sdk-coin-tao/src/lib/tokenTransferBuilder.ts b/modules/sdk-coin-tao/src/lib/tokenTransferBuilder.ts index 2b4317ff28..bacf122c6f 100644 --- a/modules/sdk-coin-tao/src/lib/tokenTransferBuilder.ts +++ b/modules/sdk-coin-tao/src/lib/tokenTransferBuilder.ts @@ -80,6 +80,7 @@ export class TokenTransferBuilder extends TransactionBuilder { * @returns {TokenTransferBuilder} This builder. */ originNetuid(netuid: string): this { + this.validateNetuid(netuid); this._originNetuid = netuid; return this; } @@ -90,6 +91,7 @@ export class TokenTransferBuilder extends TransactionBuilder { * @returns {TokenTransferBuilder} This builder. */ destinationNetuid(netuid: string): this { + this.validateNetuid(netuid); this._destinationNetuid = netuid; return this; } @@ -165,6 +167,16 @@ export class TokenTransferBuilder extends TransactionBuilder { } } + /** + * Validate the netuid. Throws an error if the netuid is not a non-negative integer. + * @param netuid The netuid to validate. + */ + validateNetuid(netuid: string): void { + if (BigInt(netuid) < 0n) { + throw new Error(`The netuid '${netuid}' is not a valid netuid`); + } + } + /** * Construct a transaction to transfer stake * diff --git a/modules/sdk-coin-tao/src/lib/tokenTransferTransaction.ts b/modules/sdk-coin-tao/src/lib/tokenTransferTransaction.ts index 6192599e14..521a925c1f 100644 --- a/modules/sdk-coin-tao/src/lib/tokenTransferTransaction.ts +++ b/modules/sdk-coin-tao/src/lib/tokenTransferTransaction.ts @@ -28,30 +28,6 @@ export class TokenTransferTransaction extends SubstrateTransaction { return result; } - /** @inheritdoc */ - loadInputsAndOutputs(): void { - super.loadInputsAndOutputs(); - - const decodedTx = decode(this._substrateTransaction, { - metadataRpc: this._substrateTransaction.metadataRpc, - registry: this._registry, - isImmortalEra: utils.isZeroHex(this._substrateTransaction.era), - }) as unknown as SubstrateInterface.DecodedTx; - const txMethod = decodedTx.method.args as SubstrateInterface.TransferStakeArgs; - - this._inputs.push({ - address: this._sender, - value: txMethod.alphaAmount, - coin: utils.getTaoTokenBySubnetId(txMethod.originNetuid).name, - }); - - this._outputs.push({ - address: txMethod.destinationColdkey, - value: txMethod.alphaAmount, - coin: utils.getTaoTokenBySubnetId(txMethod.destinationNetuid).name, - }); - } - /** @inheritdoc */ explainTransaction(): SubstrateInterface.TransactionExplanation { const result = this.toJson(); diff --git a/modules/sdk-coin-tao/test/resources/index.ts b/modules/sdk-coin-tao/test/resources/index.ts index bf1cb9ddba..74ca0d712a 100644 --- a/modules/sdk-coin-tao/test/resources/index.ts +++ b/modules/sdk-coin-tao/test/resources/index.ts @@ -177,7 +177,7 @@ export const rawTx = { }, transferStake: { signed: - '0xdd02840061b18c6dc02ddcabdeac56cb4f21a971cc41cc97640f6f85b073480008c53a0d00aadae7fa1f53e7a5c900b330ff71bee6782cf3c29a2c6f9599162381cd021ad581c74ded89f49ec79adefed64af8ff16649553523dda9cb4f017cbf15681e50ed5012103000007569f7b0675db59d19b4bd9c8c72eaabba75a9863d02b30115b8b3c3ca5c20f02548a90be061598f4b592afbd546bcb6beadb3c02f5c129df2e11b698f9543dbd41010001000300000000002000', + '0xdd02840061b18c6dc02ddcabdeac56cb4f21a971cc41cc97640f6f85b073480008c53a0d00aadae7fa1f53e7a5c900b330ff71bee6782cf3c29a2c6f9599162381cd021ad581c74ded89f49ec79adefed64af8ff16649553523dda9cb4f017cbf15681e50ed5012103000007569f7b0675db59d19b4bd9c8c72eaabba75a9863d02b30115b8b3c3ca5c20f02548a90be061598f4b592afbd546bcb6beadb3c02f5c129df2e11b698f9543dbd410c000a000300000000002000', }, }; diff --git a/modules/sdk-coin-tao/test/unit/transactionBuilder/tokenTransferBuilder.ts b/modules/sdk-coin-tao/test/unit/transactionBuilder/tokenTransferBuilder.ts index 7b5d273010..159f57a7f1 100644 --- a/modules/sdk-coin-tao/test/unit/transactionBuilder/tokenTransferBuilder.ts +++ b/modules/sdk-coin-tao/test/unit/transactionBuilder/tokenTransferBuilder.ts @@ -43,6 +43,31 @@ describe('Tao Token Transfer Builder', function () { SinonAssert.callCount(spyValidateAddress, 4); }); + + it('should validate netuid', function () { + const spyValidateAddress = spy(builder, 'validateNetuid'); + assert.throws( + () => builder.destinationNetuid('abc'), + (e: Error) => e.message === `Cannot convert abc to a BigInt` + ); + assert.throws( + () => builder.destinationNetuid('-10'), + (e: Error) => e.message === `The netuid '-10' is not a valid netuid` + ); + should.doesNotThrow(() => builder.destinationNetuid('36')); + + assert.throws( + () => builder.originNetuid('abc'), + (e: Error) => e.message === `Cannot convert abc to a BigInt` + ); + assert.throws( + () => builder.destinationNetuid('-1'), + (e: Error) => e.message === `The netuid '-1' is not a valid netuid` + ); + should.doesNotThrow(() => builder.originNetuid('64')); + + SinonAssert.callCount(spyValidateAddress, 6); + }); }); describe('build transfer stake transaction', function () { @@ -51,8 +76,8 @@ describe('Tao Token Transfer Builder', function () { .amount('9007199254740995') .destinationColdkey('5Ffp1wJCPu4hzVDTo7XaMLqZSvSadyUQmxWPDw74CBjECSoq') .hotkey('5FCPTnjevGqAuTttetBy4a24Ej3pH9fiQ8fmvP1ZkrVsLUoT') - .originNetuid('1') - .destinationNetuid('1') + .originNetuid('12') + .destinationNetuid('10') .sender({ address: sender.address }) .validity({ firstValid: 3933, maxDuration: 64 }) .referenceBlock(referenceBlock) @@ -65,7 +90,7 @@ describe('Tao Token Transfer Builder', function () { serializedTx.should.equal(rawTx.transferStake.signed); tx.toJson().should.deepEqual({ - id: '0xe5ce9ff1bbdf54d1dbd5adee8648027aa7efa99d319b041afb4b57be2042fc11', + id: '0xe5932b507a53d351aabd520487ba55ba833e0968ad18642a28f54dabeb7abf2f', sender: '5EGoFA95omzemRssELLDjVenNZ68aXyUeqtKQScXSEBvVJkr', referenceBlock: '0x149799bc9602cb5cf201f3425fb8d253b2d4e61fc119dcab3249f307f594754d', blockNumber: 3933, @@ -78,19 +103,10 @@ describe('Tao Token Transfer Builder', function () { tip: 0, destinationColdkey: '5Ffp1wJCPu4hzVDTo7XaMLqZSvSadyUQmxWPDw74CBjECSoq', hotkey: '5FCPTnjevGqAuTttetBy4a24Ej3pH9fiQ8fmvP1ZkrVsLUoT', - originNetuid: '1', - destinationNetuid: '1', + originNetuid: '12', + destinationNetuid: '10', alphaAmount: '9007199254740995', }); - tx.explainTransaction().should.containDeep({ - outputs: [ - { - address: '5Ffp1wJCPu4hzVDTo7XaMLqZSvSadyUQmxWPDw74CBjECSoq', - amount: '9007199254740995', - tokenName: 'ttao:apex', - }, - ], - }); }); it('should re-build from raw signed tx', async function () {