Skip to content

Commit

Permalink
feat: replace account class hash with constant value (#178)
Browse files Browse the repository at this point in the history
* feat: replace account class hash with constant value

* fix: remove account hash checking
  • Loading branch information
stanleyyconsensys authored Nov 20, 2023
1 parent d745354 commit f588c9c
Show file tree
Hide file tree
Showing 11 changed files with 15 additions and 94 deletions.
5 changes: 1 addition & 4 deletions packages/starknet-snap/src/createAccount.ts
Original file line number Diff line number Diff line change
Expand Up @@ -38,10 +38,7 @@ export async function createAccount(params: ApiParams, silentMode = false) {
addressIndex: addressIndexInUsed,
derivationPath,
} = await getKeysFromAddressIndex(keyDeriver, network.chainId, state, addressIndex);
const { address: contractAddress, callData: contractCallData } = getAccContractAddressAndCallData(
network.accountClassHash,
publicKey,
);
const { address: contractAddress, callData: contractCallData } = getAccContractAddressAndCallData(publicKey);
logger.log(
`createAccount:\ncontractAddress = ${contractAddress}\npublicKey = ${publicKey}\naddressIndex = ${addressIndexInUsed}`,
);
Expand Down
5 changes: 1 addition & 4 deletions packages/starknet-snap/src/estimateAccountDeployFee.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,10 +22,7 @@ export async function estimateAccDeployFee(params: ApiParams) {
addressIndex: addressIndexInUsed,
privateKey,
} = await getKeysFromAddressIndex(keyDeriver, network.chainId, state, addressIndex);
const { address: contractAddress, callData: contractCallData } = getAccContractAddressAndCallData(
network.accountClassHash,
publicKey,
);
const { address: contractAddress, callData: contractCallData } = getAccContractAddressAndCallData(publicKey);
logger.log(
`estimateAccountDeployFee:\ncontractAddress = ${contractAddress}\npublicKey = ${publicKey}\naddressIndex = ${addressIndexInUsed}`,
);
Expand Down
2 changes: 1 addition & 1 deletion packages/starknet-snap/src/estimateFee.ts
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ export async function estimateFee(params: ApiParams) {
},
];
if (!accountDeployed) {
const { callData } = getAccContractAddressAndCallData(network.accountClassHash, publicKey);
const { callData } = getAccContractAddressAndCallData(publicKey);
const deployAccountpayload = {
classHash: PROXY_CONTRACT_HASH,
contractAddress: senderAddress,
Expand Down
18 changes: 1 addition & 17 deletions packages/starknet-snap/src/recoverAccounts.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,6 @@ import { getSigner, getKeysFromAddressIndex, getAccContractAddressAndCallData }
import { getNetworkFromChainId, getValidNumber, upsertAccount } from './utils/snapUtils';
import { AccContract } from './types/snapState';
import { ApiParams, RecoverAccountsRequestParams } from './types/snapApi';
import { DialogType } from '@metamask/rpc-methods';
import { heading, panel, text } from '@metamask/snaps-ui';
import { logger } from './utils/logger';

export async function recoverAccounts(params: ApiParams) {
Expand All @@ -20,20 +18,6 @@ export async function recoverAccounts(params: ApiParams) {

logger.log(`recoverAccounts:\nstartIndex: ${startIndex}, maxScanned: ${maxScanned}, maxMissed: ${maxMissed}`);

if (!network.accountClassHash) {
await wallet.request({
method: 'snap_dialog',
params: {
type: DialogType.Alert,
content: panel([
heading('Failed to recover accounts'),
text('Recover Accounts not supported in network without class hash'),
]),
},
});
return null;
}

let i = startIndex,
j = 0;
const scannedAccounts: AccContract[] = [];
Expand All @@ -45,7 +29,7 @@ export async function recoverAccounts(params: ApiParams) {
state,
i,
);
const { address: contractAddress } = getAccContractAddressAndCallData(network.accountClassHash, publicKey);
const { address: contractAddress } = getAccContractAddressAndCallData(publicKey);
logger.log(`recoverAccounts: index ${i}:\ncontractAddress = ${contractAddress}\npublicKey = ${publicKey}`);

let signerPublicKey = '';
Expand Down
2 changes: 1 addition & 1 deletion packages/starknet-snap/src/types/snapApi.ts
Original file line number Diff line number Diff line change
Expand Up @@ -202,4 +202,4 @@ export interface SignDeclareTransactionRequestParams extends SignRequestParams,

export interface SwitchNetworkRequestParams extends BaseRequestParams {
chainId: string;
}
}
8 changes: 4 additions & 4 deletions packages/starknet-snap/src/utils/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,15 +13,15 @@ export const MAXIMUM_TOKEN_SYMBOL_LENGTH = 16;

export const TRANSFER_SELECTOR_HEX = '0x83afd3f4caedc6eebf44246fe54e38c95e3179a5ec9ea81740eca5b482d12e';

export const ACCOUNT_CLASS_HASH = '0x033434ad846cdd5f23eb73ff09fe6fddd568284a0fb7d1be20ee482f044dabe2'; // from argent-x repo
export const ACCOUNT_CLASS_HASH_V0 = '0x033434ad846cdd5f23eb73ff09fe6fddd568284a0fb7d1be20ee482f044dabe2'; // from argent-x repo

export const STARKNET_MAINNET_NETWORK: Network = {
name: 'Starknet Mainnet',
chainId: constants.StarknetChainId.SN_MAIN,
baseUrl: 'https://alpha-mainnet.starknet.io',
nodeUrl: 'https://starknet-mainnet.infura.io/v3/60c7253fb48147658095fe0460ac9ee9',
voyagerUrl: 'https://voyager.online',
accountClassHash: '0x033434ad846cdd5f23eb73ff09fe6fddd568284a0fb7d1be20ee482f044dabe2', // from argent-x repo
accountClassHash: '', // from argent-x repo
};

export const STARKNET_TESTNET_NETWORK: Network = {
Expand All @@ -30,7 +30,7 @@ export const STARKNET_TESTNET_NETWORK: Network = {
baseUrl: 'https://alpha4.starknet.io',
nodeUrl: 'https://starknet-goerli.infura.io/v3/60c7253fb48147658095fe0460ac9ee9',
voyagerUrl: 'https://goerli.voyager.online',
accountClassHash: '0x033434ad846cdd5f23eb73ff09fe6fddd568284a0fb7d1be20ee482f044dabe2', // from argent-x repo
accountClassHash: '', // from argent-x repo
};

export const STARKNET_INTEGRATION_NETWORK: Network = {
Expand All @@ -39,7 +39,7 @@ export const STARKNET_INTEGRATION_NETWORK: Network = {
baseUrl: 'https://external.integration.starknet.io',
nodeUrl: '',
voyagerUrl: '',
accountClassHash: '0x033434ad846cdd5f23eb73ff09fe6fddd568284a0fb7d1be20ee482f044dabe2', // from argent-x repo
accountClassHash: '', // from argent-x repo
};

export const ETHER_MAINNET: Erc20Token = {
Expand Down
9 changes: 0 additions & 9 deletions packages/starknet-snap/src/utils/snapUtils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -157,14 +157,6 @@ export function validateAddNetworkParams(params: AddNetworkRequestParams) {
throw new Error(`The given network Voyager URL is not an valid HTTP/HTTPS URL: ${params.networkVoyagerUrl}`);
}

if (params.accountClassHash) {
try {
validateAndParseAddress(params.accountClassHash);
} catch (err) {
throw new Error(`The given account class hash is invalid: ${params.accountClassHash}`);
}
}

if (isPreloadedNetworkChainId(params.networkChainId) || isPreloadedNetworkName(params.networkName)) {
throw new Error(
'The given network chainId or name is the same as one of the preloaded networks, and thus cannot be added',
Expand Down Expand Up @@ -425,7 +417,6 @@ export async function upsertNetwork(network: Network, wallet, mutex: Mutex, stat
storedNetwork.baseUrl = network.baseUrl;
storedNetwork.nodeUrl = network.nodeUrl;
storedNetwork.voyagerUrl = network.voyagerUrl;
storedNetwork.accountClassHash = network.accountClassHash;
}

await wallet.request({
Expand Down
10 changes: 5 additions & 5 deletions packages/starknet-snap/src/utils/starknetUtils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ import {
} from 'starknet';
import type { Hex } from '@noble/curves/abstract/utils';
import { Network, SnapState, Transaction, TransactionType } from '../types/snapState';
import { PROXY_CONTRACT_HASH, TRANSFER_SELECTOR_HEX } from './constants';
import { ACCOUNT_CLASS_HASH_V0, PROXY_CONTRACT_HASH, TRANSFER_SELECTOR_HEX } from './constants';
import { getAddressKey } from './keyPair';
import { getAccount, getAccounts, getTransactionFromVoyagerUrl, getTransactionsFromVoyagerUrl } from './snapUtils';
import { logger } from './logger';
Expand Down Expand Up @@ -400,9 +400,9 @@ export const getNextAddressIndex = (chainId: string, state: SnapState, derivatio
return uninitializedAccount?.addressIndex ?? accounts.length;
};

export const getAccContractAddressAndCallData = (accountClassHash: string, publicKey) => {
export const getAccContractAddressAndCallData = (publicKey) => {
const callData = CallData.compile({
implementation: accountClassHash,
implementation: ACCOUNT_CLASS_HASH_V0,
selector: hash.getSelectorFromName('initialize'),
calldata: CallData.compile({ signer: publicKey, guardian: '0' }),
});
Expand Down Expand Up @@ -432,7 +432,7 @@ export const getKeysFromAddress = async (
const bigIntAddress = num.toBigInt(address);
for (let i = 0; i < maxScan; i++) {
const { publicKey } = await getKeysFromAddressIndex(keyDeriver, network.chainId, state, i);
const { address: calculatedAddress } = getAccContractAddressAndCallData(network.accountClassHash, publicKey);
const { address: calculatedAddress } = getAccContractAddressAndCallData(publicKey);
if (num.toBigInt(calculatedAddress) === bigIntAddress) {
addressIndex = i;
logger.log(`getNextAddressIndex:\nFound address in scan: ${addressIndex} ${address}`);
Expand Down Expand Up @@ -474,7 +474,7 @@ export const getKeysFromAddressIndex = async (
export const isAccountDeployed = async (network: Network, publicKey: string) => {
let accountDeployed = true;
try {
const { address: signerContractAddress } = getAccContractAddressAndCallData(network.accountClassHash, publicKey);
const { address: signerContractAddress } = getAccContractAddressAndCallData(publicKey);
await getSigner(signerContractAddress, network);
} catch (err) {
accountDeployed = false;
Expand Down
23 changes: 0 additions & 23 deletions packages/starknet-snap/test/src/addNetwork.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -282,34 +282,12 @@ describe('Test function: addNetwork', function () {
}
});

it('should throw an error if the network account class hash is not valid', async function () {
const requestObject: AddNetworkRequestParams = {
networkName: 'Starknet Unit SN_GOERLI',
networkChainId: '0x534e5f474f777',
networkBaseUrl: '',
networkNodeUrl: 'http://alpha-unit-SN_GOERLI-2.starknet.io',
accountClassHash: '0x811111111111111111111111111111111111111111111111111111111111111',
// a valid Starknet hash is essentially a cario felt, which is a 251 bit positive number
// which means it can only be 63 hex character long with the leading char being [1-7]
};
apiParams.requestParams = requestObject;
let result;
try {
result = await addNetwork(apiParams);
} catch (err) {
result = err;
} finally {
expect(result).to.be.an('Error');
}
});

it('should throw an error if the network chainId is one of the preloaded network chainId', async function () {
const requestObject: AddNetworkRequestParams = {
networkName: 'Starknet Unit SN_GOERLI',
networkChainId: '0x534e5f474f45524c49',
networkBaseUrl: 'http://alpha-unit-SN_GOERLI-2.starknet.io',
networkNodeUrl: '',
accountClassHash: '0x3e327de1c40540b98d05cbcb13552008e36f0ec8d61d46956d2f9752c294328',
};
apiParams.requestParams = requestObject;
let result;
Expand All @@ -328,7 +306,6 @@ describe('Test function: addNetwork', function () {
networkChainId: STARKNET_TESTNET_NETWORK.chainId,
networkBaseUrl: STARKNET_TESTNET_NETWORK.baseUrl,
networkNodeUrl: STARKNET_TESTNET_NETWORK.nodeUrl,
accountClassHash: STARKNET_TESTNET_NETWORK.accountClassHash,
};
apiParams.requestParams = requestObject;
let result;
Expand Down
5 changes: 1 addition & 4 deletions packages/starknet-snap/test/src/createAccount.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -70,10 +70,7 @@ describe('Test function: createAccount', function () {
state,
-1,
);
const { address: contractAddress } = utils.getAccContractAddressAndCallData(
STARKNET_MAINNET_NETWORK.accountClassHash,
publicKey,
);
const { address: contractAddress } = utils.getAccContractAddressAndCallData(publicKey);
expect(walletStub.rpcStubs.snap_manageState).to.have.been.callCount(0);
expect(result.address).to.be.eq(contractAddress);
expect(state.accContracts.length).to.be.eq(0);
Expand Down
22 changes: 0 additions & 22 deletions packages/starknet-snap/test/src/recoverAccounts.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -178,26 +178,4 @@ describe('Test function: recoverAccounts', function () {
expect(result).to.be.an('Error');
}
});

it('should show confirmation box with failure msg if network accountClassHash is missing', async function () {
const maxScanned = 5;
const maxMissed = 3;
const validPublicKeys = 2;
const getSignerStub = sandbox.stub(utils, 'getSigner');
for (let i = 0; i < validPublicKeys; i++) {
getSignerStub.onCall(i).resolves(testnetPublicKeys[i]);
}
getSignerStub.throws(new Error());

const requestObject: RecoverAccountsRequestParams = {
startScanIndex: 0,
maxScanned,
maxMissed,
chainId: INVALID_NETWORK.chainId,
};
apiParams.requestParams = requestObject;
const result = await recoverAccounts(apiParams);
expect(walletStub.rpcStubs.snap_dialog).to.have.been.calledOnce;
expect(result).eql(null);
});
});

0 comments on commit f588c9c

Please sign in to comment.