diff --git a/packages/starknet-snap/src/index.ts b/packages/starknet-snap/src/index.ts index a3f778d2..46859407 100644 --- a/packages/starknet-snap/src/index.ts +++ b/packages/starknet-snap/src/index.ts @@ -4,12 +4,7 @@ import type { OnInstallHandler, OnUpdateHandler, } from '@metamask/snaps-sdk'; -import { - panel, - text, - SnapError, - MethodNotFoundError, -} from '@metamask/snaps-sdk'; +import { panel, text, MethodNotFoundError } from '@metamask/snaps-sdk'; import { addErc20Token } from './addErc20Token'; import { addNetwork } from './addNetwork'; @@ -67,6 +62,7 @@ import { STARKNET_SEPOLIA_TESTNET_NETWORK, STARKNET_TESTNET_NETWORK, } from './utils/constants'; +import { UnknownError } from './utils/exceptions'; import { getAddressKeyDeriver } from './utils/keyPair'; import { acquireLock } from './utils/lock'; import { logger } from './utils/logger'; @@ -287,7 +283,8 @@ export const onRpcRequest: OnRpcRequestHandler = async ({ request }) => { let snapError = error; if (!isSnapRpcError(error)) { - snapError = new SnapError('Unable to execute the rpc request'); + // To ensure the error meets both the SnapError format and WalletRpc format. + snapError = new UnknownError('Unable to execute the rpc request'); } logger.error( `onRpcRequest error: ${JSON.stringify(snapError.toJSON(), null, 2)}`, diff --git a/packages/starknet-snap/src/rpcs/displayPrivateKey.test.ts b/packages/starknet-snap/src/rpcs/displayPrivateKey.test.ts index 07c9faef..2fefde3d 100644 --- a/packages/starknet-snap/src/rpcs/displayPrivateKey.test.ts +++ b/packages/starknet-snap/src/rpcs/displayPrivateKey.test.ts @@ -1,11 +1,11 @@ -import { - InvalidParamsError, - UserRejectedRequestError, -} from '@metamask/snaps-sdk'; import { constants } from 'starknet'; import type { SnapState } from '../types/snapState'; import { STARKNET_SEPOLIA_TESTNET_NETWORK } from '../utils/constants'; +import { + UserRejectedOpError, + InvalidRequestParamsError, +} from '../utils/exceptions'; import { mockAccount, prepareAlertDialog, @@ -77,7 +77,7 @@ describe('displayPrivateKey', () => { ]); }); - it('throws `UserRejectedRequestError` if user denies the operation', async () => { + it('throws `UserRejectedOpError` if user denies the operation', async () => { const chainId = constants.StarknetChainId.SN_SEPOLIA; const account = await mockAccount(chainId); prepareMockAccount(account, state); @@ -89,7 +89,7 @@ describe('displayPrivateKey', () => { const request = createRequestParam(chainId, account.address); await expect(displayPrivateKey.execute(request)).rejects.toThrow( - UserRejectedRequestError, + UserRejectedOpError, ); }); @@ -108,11 +108,11 @@ describe('displayPrivateKey', () => { }, }, ])( - 'throws `InvalidParamsError` when $case', + 'throws `InvalidRequestParamsError` when $case', async ({ request }: { request: unknown }) => { await expect( displayPrivateKey.execute(request as DisplayPrivateKeyParams), - ).rejects.toThrow(InvalidParamsError); + ).rejects.toThrow(InvalidRequestParamsError); }, ); }); diff --git a/packages/starknet-snap/src/rpcs/displayPrivateKey.ts b/packages/starknet-snap/src/rpcs/displayPrivateKey.ts index 38f5092d..b1dd38ef 100644 --- a/packages/starknet-snap/src/rpcs/displayPrivateKey.ts +++ b/packages/starknet-snap/src/rpcs/displayPrivateKey.ts @@ -1,4 +1,4 @@ -import { copyable, text, UserRejectedRequestError } from '@metamask/snaps-sdk'; +import { copyable, text } from '@metamask/snaps-sdk'; import { type Infer, object, literal, assign } from 'superstruct'; import { @@ -8,6 +8,7 @@ import { alertDialog, BaseRequestStruct, } from '../utils'; +import { UserRejectedOpError } from '../utils/exceptions'; export const DisplayPrivateKeyRequestStruct = assign( object({ @@ -58,7 +59,7 @@ export class DisplayPrivateKeyRpc extends AccountRpcController< const confirmComponents = [text('Do you want to export your private key?')]; if (!(await confirmDialog(confirmComponents))) { - throw new UserRejectedRequestError() as unknown as Error; + throw new UserRejectedOpError() as unknown as Error; } const alertComponents = [ diff --git a/packages/starknet-snap/src/rpcs/estimateFee.test.ts b/packages/starknet-snap/src/rpcs/estimateFee.test.ts index bf2cdcf6..bada8c5c 100644 --- a/packages/starknet-snap/src/rpcs/estimateFee.test.ts +++ b/packages/starknet-snap/src/rpcs/estimateFee.test.ts @@ -1,4 +1,3 @@ -import { InvalidParamsError } from '@metamask/snaps-sdk'; import type { Invocations } from 'starknet'; import { constants, TransactionType } from 'starknet'; import type { Infer } from 'superstruct'; @@ -6,6 +5,7 @@ import type { Infer } from 'superstruct'; import { getEstimateFees } from '../__tests__/helper'; import { FeeTokenUnit } from '../types/snapApi'; import { STARKNET_SEPOLIA_TESTNET_NETWORK } from '../utils/constants'; +import { InvalidRequestParamsError } from '../utils/exceptions'; import * as starknetUtils from '../utils/starknetUtils'; import type { TxVersionStruct } from '../utils/superstruct'; import { mockAccount, prepareMockAccount } from './__tests__/helper'; @@ -101,9 +101,9 @@ describe('estimateFee', () => { }); }); - it('throws `InvalidParamsError` when request parameter is not correct', async () => { + it('throws `InvalidRequestParamsError` when request parameter is not correct', async () => { await expect( estimateFee.execute({} as unknown as EstimateFeeParams), - ).rejects.toThrow(InvalidParamsError); + ).rejects.toThrow(InvalidRequestParamsError); }); }); diff --git a/packages/starknet-snap/src/rpcs/executeTxn.test.ts b/packages/starknet-snap/src/rpcs/executeTxn.test.ts index 7dfdfe11..31d2f500 100644 --- a/packages/starknet-snap/src/rpcs/executeTxn.test.ts +++ b/packages/starknet-snap/src/rpcs/executeTxn.test.ts @@ -1,7 +1,3 @@ -import { - InvalidParamsError, - UserRejectedRequestError, -} from '@metamask/snaps-sdk'; import type { UniversalDetails, Call, InvokeFunctionResponse } from 'starknet'; import { constants } from 'starknet'; @@ -9,6 +5,10 @@ import callsExamples from '../__tests__/fixture/callsExamples.json'; // Assuming import { getEstimateFees } from '../__tests__/helper'; import type { FeeTokenUnit } from '../types/snapApi'; import { STARKNET_SEPOLIA_TESTNET_NETWORK } from '../utils/constants'; +import { + UserRejectedOpError, + InvalidRequestParamsError, +} from '../utils/exceptions'; import * as starknetUtils from '../utils/starknetUtils'; import { executeTxn as executeTxnUtil } from '../utils/starknetUtils'; import { @@ -179,7 +179,7 @@ describe('ExecuteTxn', () => { }, ); - it('throws UserRejectedRequestError if user cancels execution', async () => { + it('throws UserRejectedOpError if user cancels execution', async () => { callsExample = callsExamples[1]; const { request, confirmDialogSpy } = await prepareMockExecuteTxn( callsExample.hash, @@ -190,7 +190,7 @@ describe('ExecuteTxn', () => { confirmDialogSpy.mockResolvedValue(false); await expect(executeTxn.execute(request)).rejects.toThrow( - UserRejectedRequestError, + UserRejectedOpError, ); }); @@ -209,9 +209,9 @@ describe('ExecuteTxn', () => { await expect(executeTxn.execute(request)).rejects.toThrow(Error); }); - it('throws `InvalidParamsError` when request parameter is not correct', async () => { + it('throws `InvalidRequestParamsError` when request parameter is not correct', async () => { await expect( executeTxn.execute({} as unknown as ExecuteTxnParams), - ).rejects.toThrow(InvalidParamsError); + ).rejects.toThrow(InvalidRequestParamsError); }); }); diff --git a/packages/starknet-snap/src/rpcs/executeTxn.ts b/packages/starknet-snap/src/rpcs/executeTxn.ts index 3b89ff93..0da48cce 100644 --- a/packages/starknet-snap/src/rpcs/executeTxn.ts +++ b/packages/starknet-snap/src/rpcs/executeTxn.ts @@ -1,11 +1,5 @@ import type { Component, Json } from '@metamask/snaps-sdk'; -import { - heading, - row, - UserRejectedRequestError, - text, - divider, -} from '@metamask/snaps-sdk'; +import { heading, row, text, divider } from '@metamask/snaps-sdk'; import convert from 'ethereum-unit-converter'; import type { Call, Calldata } from 'starknet'; import { constants, TransactionStatus, TransactionType } from 'starknet'; @@ -27,6 +21,7 @@ import { CallsStruct, mapDeprecatedParams, } from '../utils'; +import { UserRejectedOpError } from '../utils/exceptions'; import { logger } from '../utils/logger'; import { createAccount, @@ -140,7 +135,7 @@ export class ExecuteTxnRpc extends AccountRpcController< version, )) ) { - throw new UserRejectedRequestError() as unknown as Error; + throw new UserRejectedOpError() as unknown as Error; } if (!accountDeployed) { diff --git a/packages/starknet-snap/src/rpcs/sign-declare-transaction.test.ts b/packages/starknet-snap/src/rpcs/sign-declare-transaction.test.ts index 5cb8f1ee..73defc9b 100644 --- a/packages/starknet-snap/src/rpcs/sign-declare-transaction.test.ts +++ b/packages/starknet-snap/src/rpcs/sign-declare-transaction.test.ts @@ -1,13 +1,13 @@ -import { - InvalidParamsError, - UserRejectedRequestError, -} from '@metamask/snaps-sdk'; import type { DeclareSignerDetails } from 'starknet'; import { constants } from 'starknet'; import type { SnapState } from '../types/snapState'; import { toJson } from '../utils'; import { STARKNET_SEPOLIA_TESTNET_NETWORK } from '../utils/constants'; +import { + UserRejectedOpError, + InvalidRequestParamsError, +} from '../utils/exceptions'; import * as starknetUtils from '../utils/starknetUtils'; import { mockAccount, @@ -108,7 +108,7 @@ describe('signDeclareTransaction', () => { ]); }); - it('throws `UserRejectedRequestError` if user denied the operation', async () => { + it('throws `UserRejectedOpError` if user denied the operation', async () => { const chainId = constants.StarknetChainId.SN_SEPOLIA; const account = await mockAccount(chainId); @@ -120,15 +120,15 @@ describe('signDeclareTransaction', () => { const request = createRequest(chainId, account.address); await expect(signDeclareTransaction.execute(request)).rejects.toThrow( - UserRejectedRequestError, + UserRejectedOpError, ); }); - it('throws `InvalidParamsError` when request parameter is not correct', async () => { + it('throws `InvalidRequestParamsError` when request parameter is not correct', async () => { await expect( signDeclareTransaction.execute( {} as unknown as SignDeclareTransactionParams, ), - ).rejects.toThrow(InvalidParamsError); + ).rejects.toThrow(InvalidRequestParamsError); }); }); diff --git a/packages/starknet-snap/src/rpcs/sign-declare-transaction.ts b/packages/starknet-snap/src/rpcs/sign-declare-transaction.ts index f9f784a4..9a9d92e1 100644 --- a/packages/starknet-snap/src/rpcs/sign-declare-transaction.ts +++ b/packages/starknet-snap/src/rpcs/sign-declare-transaction.ts @@ -1,10 +1,5 @@ import type { Component } from '@metamask/snaps-sdk'; -import { - heading, - row, - text, - UserRejectedRequestError, -} from '@metamask/snaps-sdk'; +import { heading, row, text } from '@metamask/snaps-sdk'; import type { DeclareSignerDetails } from 'starknet'; import type { Infer } from 'superstruct'; import { array, object, string, assign } from 'superstruct'; @@ -18,6 +13,7 @@ import { DeclareSignDetailsStruct, mapDeprecatedParams, } from '../utils'; +import { UserRejectedOpError } from '../utils/exceptions'; import { signDeclareTransaction as signDeclareTransactionUtil } from '../utils/starknetUtils'; export const SignDeclareTransactionRequestStruct = assign( @@ -87,7 +83,7 @@ export class SignDeclareTransactionRpc extends AccountRpcController< ): Promise { const { details } = params; if (!(await this.getSignDeclareTransactionConsensus(details))) { - throw new UserRejectedRequestError() as unknown as Error; + throw new UserRejectedOpError() as unknown as Error; } return (await signDeclareTransactionUtil( diff --git a/packages/starknet-snap/src/rpcs/signMessage.test.ts b/packages/starknet-snap/src/rpcs/signMessage.test.ts index b44a66cd..50b03727 100644 --- a/packages/starknet-snap/src/rpcs/signMessage.test.ts +++ b/packages/starknet-snap/src/rpcs/signMessage.test.ts @@ -1,13 +1,13 @@ -import { - InvalidParamsError, - UserRejectedRequestError, -} from '@metamask/snaps-sdk'; import { constants } from 'starknet'; import typedDataExample from '../__tests__/fixture/typedDataExample.json'; import type { SnapState } from '../types/snapState'; import { toJson } from '../utils'; import { STARKNET_SEPOLIA_TESTNET_NETWORK } from '../utils/constants'; +import { + UserRejectedOpError, + InvalidRequestParamsError, +} from '../utils/exceptions'; import * as starknetUtils from '../utils/starknetUtils'; import { mockAccount, @@ -89,7 +89,7 @@ describe('signMessage', () => { ]); }); - it('throws `UserRejectedRequestError` if user denied the operation', async () => { + it('throws `UserRejectedOpError` if user denied the operation', async () => { const account = await mockAccount(constants.StarknetChainId.SN_SEPOLIA); prepareMockAccount(account, state); @@ -105,13 +105,13 @@ describe('signMessage', () => { }; await expect(signMessage.execute(request)).rejects.toThrow( - UserRejectedRequestError, + UserRejectedOpError, ); }); - it('throws `InvalidParamsError` when request parameter is not correct', async () => { + it('throws `InvalidRequestParamsError` when request parameter is not correct', async () => { await expect( signMessage.execute({} as unknown as SignMessageParams), - ).rejects.toThrow(InvalidParamsError); + ).rejects.toThrow(InvalidRequestParamsError); }); }); diff --git a/packages/starknet-snap/src/rpcs/signMessage.ts b/packages/starknet-snap/src/rpcs/signMessage.ts index 896bcfed..79d8d692 100644 --- a/packages/starknet-snap/src/rpcs/signMessage.ts +++ b/packages/starknet-snap/src/rpcs/signMessage.ts @@ -1,10 +1,5 @@ import type { Component } from '@metamask/snaps-sdk'; -import { - heading, - row, - text, - UserRejectedRequestError, -} from '@metamask/snaps-sdk'; +import { heading, row, text } from '@metamask/snaps-sdk'; import type { Infer } from 'superstruct'; import { array, object, string, assign } from 'superstruct'; @@ -18,6 +13,7 @@ import { AccountRpcController, mapDeprecatedParams, } from '../utils'; +import { UserRejectedOpError } from '../utils/exceptions'; import { signMessage as signMessageUtil } from '../utils/starknetUtils'; export const SignMessageRequestStruct = assign( @@ -84,7 +80,7 @@ export class SignMessageRpc extends AccountRpcController< enableAuthorize && !(await this.getSignMessageConsensus(typedDataMessage, address)) ) { - throw new UserRejectedRequestError() as unknown as Error; + throw new UserRejectedOpError() as unknown as Error; } return await signMessageUtil( diff --git a/packages/starknet-snap/src/rpcs/signTransaction.test.ts b/packages/starknet-snap/src/rpcs/signTransaction.test.ts index 2c7e1e14..d4f37ec2 100644 --- a/packages/starknet-snap/src/rpcs/signTransaction.test.ts +++ b/packages/starknet-snap/src/rpcs/signTransaction.test.ts @@ -1,7 +1,3 @@ -import { - InvalidParamsError, - UserRejectedRequestError, -} from '@metamask/snaps-sdk'; import type { InvocationsSignerDetails } from 'starknet'; import { constants } from 'starknet'; @@ -9,6 +5,10 @@ import transactionExample from '../__tests__/fixture/transactionExample.json'; / import type { SnapState } from '../types/snapState'; import { toJson } from '../utils'; import { STARKNET_SEPOLIA_TESTNET_NETWORK } from '../utils/constants'; +import { + UserRejectedOpError, + InvalidRequestParamsError, +} from '../utils/exceptions'; import * as starknetUtils from '../utils/starknetUtils'; import { mockAccount, @@ -118,7 +118,7 @@ describe('signTransaction', () => { expect(confirmDialogSpy).not.toHaveBeenCalled(); }); - it('throws `UserRejectedRequestError` if user denied the operation', async () => { + it('throws `UserRejectedOpError` if user denied the operation', async () => { const chainId = constants.StarknetChainId.SN_SEPOLIA; const account = await mockAccount(chainId); prepareMockAccount(account, state); @@ -127,13 +127,13 @@ describe('signTransaction', () => { const request = createRequestParam(chainId, account.address, true); await expect(signTransaction.execute(request)).rejects.toThrow( - UserRejectedRequestError, + UserRejectedOpError, ); }); - it('throws `InvalidParamsError` when request parameter is not correct', async () => { + it('throws `InvalidRequestParamsError` when request parameter is not correct', async () => { await expect( signTransaction.execute({} as unknown as SignTransactionParams), - ).rejects.toThrow(InvalidParamsError); + ).rejects.toThrow(InvalidRequestParamsError); }); }); diff --git a/packages/starknet-snap/src/rpcs/signTransaction.ts b/packages/starknet-snap/src/rpcs/signTransaction.ts index 6f66350e..592ec8e9 100644 --- a/packages/starknet-snap/src/rpcs/signTransaction.ts +++ b/packages/starknet-snap/src/rpcs/signTransaction.ts @@ -1,10 +1,5 @@ import type { DialogResult } from '@metamask/snaps-sdk'; -import { - heading, - row, - text, - UserRejectedRequestError, -} from '@metamask/snaps-sdk'; +import { heading, row, text } from '@metamask/snaps-sdk'; import type { Call, InvocationsSignerDetails } from 'starknet'; import type { Infer } from 'superstruct'; import { array, object, string, assign, any } from 'superstruct'; @@ -19,6 +14,7 @@ import { toJson, mapDeprecatedParams, } from '../utils'; +import { UserRejectedOpError } from '../utils/exceptions'; import { signTransactions } from '../utils/starknetUtils'; export const SignTransactionRequestStruct = assign( @@ -93,7 +89,7 @@ export class SignTransactionRpc extends AccountRpcController< transactions as unknown as Call[], )) ) { - throw new UserRejectedRequestError() as unknown as Error; + throw new UserRejectedOpError() as unknown as Error; } return (await signTransactions( diff --git a/packages/starknet-snap/src/rpcs/verify-signature.test.ts b/packages/starknet-snap/src/rpcs/verify-signature.test.ts index e69c4327..037da54b 100644 --- a/packages/starknet-snap/src/rpcs/verify-signature.test.ts +++ b/packages/starknet-snap/src/rpcs/verify-signature.test.ts @@ -1,9 +1,9 @@ -import { InvalidParamsError } from '@metamask/snaps-sdk'; import { constants } from 'starknet'; import typedDataExample from '../__tests__/fixture/typedDataExample.json'; import type { SnapState } from '../types/snapState'; import { STARKNET_SEPOLIA_TESTNET_NETWORK } from '../utils/constants'; +import { InvalidRequestParamsError } from '../utils/exceptions'; import * as starknetUtils from '../utils/starknetUtils'; import { mockAccount, prepareMockAccount } from './__tests__/helper'; import { verifySignature } from './verify-signature'; @@ -67,9 +67,9 @@ describe('verifySignature', () => { expect(result).toBe(false); }); - it('throws `InvalidParamsError` when request parameter is not correct', async () => { + it('throws `InvalidRequestParamsError` when request parameter is not correct', async () => { await expect( verifySignature.execute({} as unknown as VerifySignatureParams), - ).rejects.toThrow(InvalidParamsError); + ).rejects.toThrow(InvalidRequestParamsError); }); }); diff --git a/packages/starknet-snap/src/utils/error.test.ts b/packages/starknet-snap/src/utils/error.test.ts index 140bb608..1b23fb54 100644 --- a/packages/starknet-snap/src/utils/error.test.ts +++ b/packages/starknet-snap/src/utils/error.test.ts @@ -18,7 +18,17 @@ import { SnapError, } from '@metamask/snaps-sdk'; -import { isSnapRpcError } from './error'; +import { + createWalletRpcErrorWrapper, + isSnapRpcError, + WalletRpcErrorCode, +} from './error'; +import { + InvalidNetworkError, + UnknownError, + UserRejectedOpError, + InvalidRequestParamsError, +} from './exceptions'; describe('isSnapRpcError', () => { it('returns true for a Snap RPC error', () => { @@ -42,7 +52,14 @@ describe('isSnapRpcError', () => { LimitExceededError, ]; - for (const ErrorCtor of snapErrors) { + const customSnapErrors = [ + InvalidNetworkError, + UserRejectedOpError, + UnknownError, + InvalidRequestParamsError, + ]; + + for (const ErrorCtor of [...snapErrors, ...customSnapErrors]) { const error = new ErrorCtor('snap error message'); expect(isSnapRpcError(error)).toBe(true); } @@ -53,3 +70,19 @@ describe('isSnapRpcError', () => { expect(isSnapRpcError(error)).toBe(false); }); }); + +describe('createWalletRpcErrorWrapper', () => { + it('returns a serialized SnapError', () => { + const wrapper = createWalletRpcErrorWrapper( + WalletRpcErrorCode.InvalidRequest, + { someData: 'data' }, + ); + + expect(wrapper).toStrictEqual({ + walletRpcError: { + someData: 'data', + code: WalletRpcErrorCode.InvalidRequest, + }, + }); + }); +}); diff --git a/packages/starknet-snap/src/utils/error.ts b/packages/starknet-snap/src/utils/error.ts index 2bdfebcf..d9feafee 100644 --- a/packages/starknet-snap/src/utils/error.ts +++ b/packages/starknet-snap/src/utils/error.ts @@ -1,3 +1,4 @@ +import type { Json } from '@metamask/snaps-sdk'; import { MethodNotFoundError, UserRejectedRequestError, @@ -46,3 +47,31 @@ export function isSnapRpcError(error: Error): boolean { ]; return errors.some((errType) => error instanceof errType); } + +// The error code is following the Starknet Wallet RPC 0.7.2 specification. +export enum WalletRpcErrorCode { + InvalidErc20 = 111, + InvalidNetwork = 112, + UserDeny = 113, + InvalidRequest = 114, + AccountAlreadyDeployed = 115, + Unknown = 163, +} + +/** + * Creates a wallet RPC error wrapper for custom snap error. + * + * @param code - The `WalletRpcErrorCode` error code. + * @param [data] - The error data. + */ +export function createWalletRpcErrorWrapper( + code: WalletRpcErrorCode, + data?: Record, +) { + return { + walletRpcError: { + ...data, + code, + }, + }; +} diff --git a/packages/starknet-snap/src/utils/exceptions.ts b/packages/starknet-snap/src/utils/exceptions.ts index d91b7d14..7c8ffe8e 100644 --- a/packages/starknet-snap/src/utils/exceptions.ts +++ b/packages/starknet-snap/src/utils/exceptions.ts @@ -1,4 +1,10 @@ -import { SnapError } from '@metamask/snaps-sdk'; +import { + InvalidParamsError, + SnapError, + UserRejectedRequestError, +} from '@metamask/snaps-sdk'; + +import { createWalletRpcErrorWrapper, WalletRpcErrorCode } from './error'; // Extend SnapError to allow error message visible to client export class UpgradeRequiredError extends SnapError { @@ -15,3 +21,36 @@ export class DeployRequiredError extends SnapError { ); } } + +export class InvalidNetworkError extends SnapError { + constructor(message?: string) { + super( + message ?? 'Network not Supported', + createWalletRpcErrorWrapper(WalletRpcErrorCode.InvalidNetwork), + ); + } +} + +export class UserRejectedOpError extends UserRejectedRequestError { + constructor(message?: string) { + super(message, createWalletRpcErrorWrapper(WalletRpcErrorCode.UserDeny)); + } +} + +export class InvalidRequestParamsError extends InvalidParamsError { + constructor(message?: string) { + super( + message, + createWalletRpcErrorWrapper(WalletRpcErrorCode.InvalidRequest), + ); + } +} + +export class UnknownError extends SnapError { + constructor(message?: string) { + super( + message ?? 'Unknown Error', + createWalletRpcErrorWrapper(WalletRpcErrorCode.Unknown), + ); + } +} diff --git a/packages/starknet-snap/src/utils/rpc.test.ts b/packages/starknet-snap/src/utils/rpc.test.ts index 38268d9e..d8f01ad7 100644 --- a/packages/starknet-snap/src/utils/rpc.test.ts +++ b/packages/starknet-snap/src/utils/rpc.test.ts @@ -1,4 +1,3 @@ -import { InvalidParamsError, SnapError } from '@metamask/snaps-sdk'; import { constants } from 'starknet'; import { object, string } from 'superstruct'; import type { Struct, Infer } from 'superstruct'; @@ -7,6 +6,7 @@ import type { StarknetAccount } from '../__tests__/helper'; import { generateAccounts } from '../__tests__/helper'; import type { SnapState } from '../types/snapState'; import { STARKNET_SEPOLIA_TESTNET_NETWORK } from './constants'; +import { InvalidRequestParamsError, UnknownError } from './exceptions'; import { AccountRpcController, RpcController, @@ -37,14 +37,14 @@ describe('validateRequest', () => { ).not.toThrow(); }); - it('throws `InvalidParamsError` if the request is invalid', () => { + it('throws `InvalidRequestParamsError` if the request is invalid', () => { const requestParams = { signerAddress: 1234, }; expect(() => validateRequest(requestParams, validateStruct as unknown as Struct), - ).toThrow(InvalidParamsError); + ).toThrow(InvalidRequestParamsError); }); }); @@ -62,7 +62,7 @@ describe('validateResponse', () => { expect(() => validateResponse(response, validateStruct as unknown as Struct), - ).toThrow(new SnapError('Invalid Response')); + ).toThrow(new UnknownError('Invalid Response')); }); }); diff --git a/packages/starknet-snap/src/utils/rpc.ts b/packages/starknet-snap/src/utils/rpc.ts index b4a8809e..70571a92 100644 --- a/packages/starknet-snap/src/utils/rpc.ts +++ b/packages/starknet-snap/src/utils/rpc.ts @@ -1,10 +1,10 @@ import type { getBIP44ChangePathString } from '@metamask/key-tree/dist/types/utils'; import type { Json } from '@metamask/snaps-sdk'; -import { InvalidParamsError, SnapError } from '@metamask/snaps-sdk'; import type { Struct } from 'superstruct'; import { assert } from 'superstruct'; import type { Network, SnapState } from '../types/snapState'; +import { InvalidRequestParamsError, UnknownError } from './exceptions'; import { logger } from './logger'; import { getBip44Deriver, getStateData } from './snap'; import { @@ -19,13 +19,13 @@ import { getKeysFromAddress } from './starknetUtils'; * @template Params - The expected structure of the request parameters. * @param requestParams - The request parameters to validate. * @param struct - The expected structure of the request parameters. - * @throws {InvalidParamsError} If the request parameters do not conform to the expected structure. + * @throws {InvalidRequestParamsError} If the request parameters do not conform to the expected structure. */ export function validateRequest(requestParams: Params, struct: Struct) { try { assert(requestParams, struct); } catch (error) { - throw new InvalidParamsError(error.message) as unknown as Error; + throw new InvalidRequestParamsError(error.message) as unknown as Error; } } @@ -41,7 +41,7 @@ export function validateResponse(response: Params, struct: Struct) { try { assert(response, struct); } catch (error) { - throw new SnapError('Invalid Response') as unknown as Error; + throw new UnknownError('Invalid Response') as unknown as Error; } }