Skip to content

Commit a0dd077

Browse files
committed
feat(1671): code review adjustments
Signed-off-by: matevszm <mateusz.marcinkowski@blockydevs.com>
1 parent b92aafa commit a0dd077

File tree

2 files changed

+172
-0
lines changed

2 files changed

+172
-0
lines changed

docs/output-schemas-guide.md

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -368,12 +368,22 @@ interface CommandOutputSpec {
368368
"supplyType": "FINITE",
369369
"transactionId": "0.0.123@1700000000.123456789",
370370
"adminAccountId": "0.0.12345",
371+
"adminPublicKey": "302a300506032b6570032100...",
371372
"supplyAccountId": "0.0.12345",
373+
"supplyPublicKey": "302a300506032b6570032100...",
374+
"freezePublicKey": "302a300506032b6570032100...",
375+
"wipePublicKey": "302a300506032b6570032100...",
376+
"pausePublicKey": "302a300506032b6570032100...",
377+
"kycPublicKey": "302a300506032b6570032100...",
378+
"feeSchedulePublicKey": "302a300506032b6570032100...",
379+
"metadataPublicKey": "302a300506032b6570032100...",
372380
"alias": "my-nft",
373381
"network": "testnet"
374382
}
375383
```
376384

385+
All key fields (`adminPublicKey`, `supplyPublicKey`, `freezePublicKey`, `wipePublicKey`, `pausePublicKey`, `kycPublicKey`, `feeSchedulePublicKey`, `metadataPublicKey`) are optional and only appear when the corresponding key was provided.
386+
377387
#### `token mint-ft`
378388

379389
**Output**:

src/plugins/token/__tests__/unit/create-nft.test.ts

Lines changed: 162 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import type { CommandHandlerArgs } from '@/core/plugins/plugin.interface';
2+
import type { TokenCreateNftOutput } from '@/plugins/token/commands/create-nft/output';
23

34
import { assertOutput } from '@/__tests__/utils/assert-output';
45
import { AliasType } from '@/core/services/alias/alias-service.interface';
@@ -14,6 +15,7 @@ import {
1415
expectedNftTransactionParams,
1516
makeNftCreateCommandArgs,
1617
mockAccountIds,
18+
mockAccountKeyPairs,
1719
mockTransactions,
1820
} from './helpers/fixtures';
1921
import {
@@ -173,7 +175,167 @@ describe('tokenCreateNftHandler', () => {
173175
});
174176
});
175177

178+
describe('optional key scenarios', () => {
179+
test('should create NFT with all optional keys', async () => {
180+
const mockSaveToken = jest.fn();
181+
const mockSignResult = makeTransactionResult({
182+
tokenId: mockAccountIds.treasury,
183+
});
184+
185+
MockedHelper.mockImplementation(() => ({
186+
saveToken: mockSaveToken,
187+
}));
188+
189+
const { api, tokenTransactions } = makeApiMocks({
190+
tokenTransactions: {
191+
createTokenTransaction: jest
192+
.fn()
193+
.mockReturnValue(mockTransactions.token),
194+
},
195+
txExecute: {
196+
execute: jest.fn().mockResolvedValue(mockSignResult),
197+
},
198+
alias: {
199+
resolve: jest.fn().mockImplementation((alias, type) => {
200+
if (type === AliasType.Account && alias === 'treasury-account') {
201+
return {
202+
entityId: '0.0.123456',
203+
publicKey: '302a300506032b6570032100' + '1'.repeat(64),
204+
keyRefId: 'treasury-key-ref-id',
205+
};
206+
}
207+
return null;
208+
}),
209+
},
210+
});
211+
212+
const logger = makeLogger();
213+
const args: CommandHandlerArgs = {
214+
args: {
215+
tokenName: 'TestNFT',
216+
symbol: 'TNFT',
217+
supplyType: SupplyType.INFINITE,
218+
treasury: 'treasury-account',
219+
freezeKey: mockAccountKeyPairs.freeze,
220+
wipeKey: mockAccountKeyPairs.wipe,
221+
pauseKey: mockAccountKeyPairs.pause,
222+
kycKey: mockAccountKeyPairs.kyc,
223+
feeScheduleKey: mockAccountKeyPairs.feeSchedule,
224+
metadataKey: mockAccountKeyPairs.supply,
225+
},
226+
api,
227+
state: api.state,
228+
config: api.config,
229+
logger,
230+
};
231+
232+
const result = await tokenCreateNft(args);
233+
234+
expect(tokenTransactions.createTokenTransaction).toHaveBeenCalledWith(
235+
expect.objectContaining({
236+
freezePublicKey: expect.any(Object),
237+
wipePublicKey: expect.any(Object),
238+
pausePublicKey: expect.any(Object),
239+
kycPublicKey: expect.any(Object),
240+
feeSchedulePublicKey: expect.any(Object),
241+
metadataPublicKey: expect.any(Object),
242+
}),
243+
);
244+
assertOutput(result.result, TokenCreateNftOutputSchema);
245+
const output = result.result as TokenCreateNftOutput;
246+
expect(output.freezePublicKey).toBeDefined();
247+
expect(output.wipePublicKey).toBeDefined();
248+
expect(output.pausePublicKey).toBeDefined();
249+
expect(output.kycPublicKey).toBeDefined();
250+
expect(output.feeSchedulePublicKey).toBeDefined();
251+
expect(output.metadataPublicKey).toBeDefined();
252+
});
253+
254+
test('should create NFT with lifecycle params', async () => {
255+
const mockSaveToken = jest.fn();
256+
const mockSignResult = makeTransactionResult({
257+
tokenId: mockAccountIds.treasury,
258+
});
259+
260+
MockedHelper.mockImplementation(() => ({
261+
saveToken: mockSaveToken,
262+
}));
263+
264+
const { api, tokenTransactions } = makeApiMocks({
265+
tokenTransactions: {
266+
createTokenTransaction: jest
267+
.fn()
268+
.mockReturnValue(mockTransactions.token),
269+
},
270+
txExecute: {
271+
execute: jest.fn().mockResolvedValue(mockSignResult),
272+
},
273+
alias: {
274+
resolve: jest.fn().mockImplementation((alias, type) => {
275+
if (type === AliasType.Account && alias === 'treasury-account') {
276+
return {
277+
entityId: '0.0.123456',
278+
publicKey: '302a300506032b6570032100' + '1'.repeat(64),
279+
keyRefId: 'treasury-key-ref-id',
280+
};
281+
}
282+
return null;
283+
}),
284+
},
285+
});
286+
287+
const logger = makeLogger();
288+
const args: CommandHandlerArgs = {
289+
args: {
290+
tokenName: 'TestNFT',
291+
symbol: 'TNFT',
292+
supplyType: SupplyType.INFINITE,
293+
treasury: 'treasury-account',
294+
autoRenewPeriod: 7776000,
295+
autoRenewAccountId: '0.0.100000',
296+
expirationTime: '2027-01-01T00:00:00Z',
297+
},
298+
api,
299+
state: api.state,
300+
config: api.config,
301+
logger,
302+
};
303+
304+
const result = await tokenCreateNft(args);
305+
306+
expect(tokenTransactions.createTokenTransaction).toHaveBeenCalledWith(
307+
expect.objectContaining({
308+
autoRenewPeriod: 7776000,
309+
autoRenewAccountId: '0.0.100000',
310+
expirationTime: expect.any(Date),
311+
}),
312+
);
313+
assertOutput(result.result, TokenCreateNftOutputSchema);
314+
});
315+
});
316+
176317
describe('validation scenarios', () => {
318+
test('should reject freezeDefault without freezeKey', async () => {
319+
const { api } = makeApiMocks();
320+
const logger = makeLogger();
321+
const args: CommandHandlerArgs = {
322+
args: {
323+
tokenName: 'TestNFT',
324+
symbol: 'TNFT',
325+
supplyType: SupplyType.INFINITE,
326+
freezeDefault: true,
327+
},
328+
api,
329+
state: api.state,
330+
config: api.config,
331+
logger,
332+
};
333+
334+
await expect(tokenCreateNft(args)).rejects.toThrow(
335+
/freezeDefault requires freezeKey/,
336+
);
337+
});
338+
177339
test('should exit with error when no credentials found', async () => {
178340
// Arrange
179341
const { api, keyResolver } = makeApiMocks();

0 commit comments

Comments
 (0)