From dbf53b6e57948e433186cae6209998dece04fe4a Mon Sep 17 00:00:00 2001 From: Toni Tabak Date: Wed, 18 Oct 2023 11:29:45 +0200 Subject: [PATCH] feat: wallet deploy contract and patches --- package-lock.json | 95 +++++++++++++++++++++++----------------- src/account/default.ts | 40 ++--------------- src/account/wallet.ts | 21 +++++++-- src/utils/transaction.ts | 59 +++++++++++++++++++++++-- 4 files changed, 130 insertions(+), 85 deletions(-) diff --git a/package-lock.json b/package-lock.json index bf59e9bf5..8d9225dc9 100644 --- a/package-lock.json +++ b/package-lock.json @@ -123,11 +123,13 @@ } }, "node_modules/@babel/code-frame": { - "version": "7.22.5", + "version": "7.22.13", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.22.13.tgz", + "integrity": "sha512-XktuhWlJ5g+3TJXc5upd9Ks1HutSArik6jf2eAjYFyIOf4ej3RN+184cZbzDvbPnuTJIUhPKKJE3cIsYTiAT3w==", "dev": true, - "license": "MIT", "dependencies": { - "@babel/highlight": "^7.22.5" + "@babel/highlight": "^7.22.13", + "chalk": "^2.4.2" }, "engines": { "node": ">=6.9.0" @@ -171,11 +173,12 @@ } }, "node_modules/@babel/generator": { - "version": "7.22.5", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.23.0.tgz", + "integrity": "sha512-lN85QRR+5IbYrMWM6Y4pE/noaQtg4pNiqeNGX60eqOfo6gtEj6uw/JagelB8vVztSd7R6M5n1+PQkDbHbBRU4g==", "dev": true, - "license": "MIT", "dependencies": { - "@babel/types": "^7.22.5", + "@babel/types": "^7.23.0", "@jridgewell/gen-mapping": "^0.3.2", "@jridgewell/trace-mapping": "^0.3.17", "jsesc": "^2.5.1" @@ -279,20 +282,22 @@ } }, "node_modules/@babel/helper-environment-visitor": { - "version": "7.22.5", + "version": "7.22.20", + "resolved": "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.22.20.tgz", + "integrity": "sha512-zfedSIzFhat/gFhWfHtgWvlec0nqB9YEIVrpuwjruLlXfUSnA8cJB0miHKwqDnQ7d32aKo2xt88/xZptwxbfhA==", "dev": true, - "license": "MIT", "engines": { "node": ">=6.9.0" } }, "node_modules/@babel/helper-function-name": { - "version": "7.22.5", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.23.0.tgz", + "integrity": "sha512-OErEqsrxjZTJciZ4Oo+eoZqeW9UIiOcuYKRJA4ZAgV9myA+pOXhhmpfNCKjEH/auVfEYVFJ6y1Tc4r0eIApqiw==", "dev": true, - "license": "MIT", "dependencies": { - "@babel/template": "^7.22.5", - "@babel/types": "^7.22.5" + "@babel/template": "^7.22.15", + "@babel/types": "^7.23.0" }, "engines": { "node": ">=6.9.0" @@ -424,9 +429,10 @@ } }, "node_modules/@babel/helper-split-export-declaration": { - "version": "7.22.5", + "version": "7.22.6", + "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.22.6.tgz", + "integrity": "sha512-AsUnxuLhRYsisFiaJwvp1QF+I3KjD5FOxut14q/GzovUe6orHLesW2C7d754kRm53h5gqrz6sFl6sxc4BVtE/g==", "dev": true, - "license": "MIT", "dependencies": { "@babel/types": "^7.22.5" }, @@ -443,9 +449,10 @@ } }, "node_modules/@babel/helper-validator-identifier": { - "version": "7.22.5", + "version": "7.22.20", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.22.20.tgz", + "integrity": "sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A==", "dev": true, - "license": "MIT", "engines": { "node": ">=6.9.0" } @@ -486,12 +493,13 @@ } }, "node_modules/@babel/highlight": { - "version": "7.22.5", + "version": "7.22.20", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.22.20.tgz", + "integrity": "sha512-dkdMCN3py0+ksCgYmGG8jKeGA/8Tk+gJwSYYlFGxG5lmhfKNoAy004YpLxpS1W2J8m/EK2Ew+yOs9pVRwO89mg==", "dev": true, - "license": "MIT", "dependencies": { - "@babel/helper-validator-identifier": "^7.22.5", - "chalk": "^2.0.0", + "@babel/helper-validator-identifier": "^7.22.20", + "chalk": "^2.4.2", "js-tokens": "^4.0.0" }, "engines": { @@ -499,9 +507,10 @@ } }, "node_modules/@babel/parser": { - "version": "7.22.5", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.23.0.tgz", + "integrity": "sha512-vvPKKdMemU85V9WE/l5wZEmImpCtLqbnTvqDS2U1fJ96KrxoW7KrXhNsNCblQlg8Ck4b85yxdTyelsMUgFUXiw==", "dev": true, - "license": "MIT", "bin": { "parser": "bin/babel-parser.js" }, @@ -1705,31 +1714,33 @@ } }, "node_modules/@babel/template": { - "version": "7.22.5", + "version": "7.22.15", + "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.22.15.tgz", + "integrity": "sha512-QPErUVm4uyJa60rkI73qneDacvdvzxshT3kksGqlGWYdOTIUOwJ7RDUL8sGqslY1uXWSL6xMFKEXDS3ox2uF0w==", "dev": true, - "license": "MIT", "dependencies": { - "@babel/code-frame": "^7.22.5", - "@babel/parser": "^7.22.5", - "@babel/types": "^7.22.5" + "@babel/code-frame": "^7.22.13", + "@babel/parser": "^7.22.15", + "@babel/types": "^7.22.15" }, "engines": { "node": ">=6.9.0" } }, "node_modules/@babel/traverse": { - "version": "7.22.5", + "version": "7.23.2", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.23.2.tgz", + "integrity": "sha512-azpe59SQ48qG6nu2CzcMLbxUudtN+dOM9kDbUqGq3HXUJRlo7i8fvPoxQUzYgLZ4cMVmuZgm8vvBpNeRhd6XSw==", "dev": true, - "license": "MIT", "dependencies": { - "@babel/code-frame": "^7.22.5", - "@babel/generator": "^7.22.5", - "@babel/helper-environment-visitor": "^7.22.5", - "@babel/helper-function-name": "^7.22.5", + "@babel/code-frame": "^7.22.13", + "@babel/generator": "^7.23.0", + "@babel/helper-environment-visitor": "^7.22.20", + "@babel/helper-function-name": "^7.23.0", "@babel/helper-hoist-variables": "^7.22.5", - "@babel/helper-split-export-declaration": "^7.22.5", - "@babel/parser": "^7.22.5", - "@babel/types": "^7.22.5", + "@babel/helper-split-export-declaration": "^7.22.6", + "@babel/parser": "^7.23.0", + "@babel/types": "^7.23.0", "debug": "^4.1.0", "globals": "^11.1.0" }, @@ -1738,12 +1749,13 @@ } }, "node_modules/@babel/types": { - "version": "7.22.5", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.23.0.tgz", + "integrity": "sha512-0oIyUfKoI3mSqMvsxBdclDwxXKXAUA8v/apZbc+iSyARYou1o8ZGDxbUYyLFoW2arqS2jDGqJuZvv1d/io1axg==", "dev": true, - "license": "MIT", "dependencies": { "@babel/helper-string-parser": "^7.22.5", - "@babel/helper-validator-identifier": "^7.22.5", + "@babel/helper-validator-identifier": "^7.22.20", "to-fast-properties": "^2.0.0" }, "engines": { @@ -9856,8 +9868,9 @@ }, "node_modules/js-tokens": { "version": "4.0.0", - "dev": true, - "license": "MIT" + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true }, "node_modules/js-yaml": { "version": "4.1.0", diff --git a/src/account/default.ts b/src/account/default.ts index 1c85d96b6..0097841b4 100644 --- a/src/account/default.ts +++ b/src/account/default.ts @@ -44,7 +44,6 @@ import { } from '../types'; import { CallData } from '../utils/calldata'; import { extractContractHashes, isSierra } from '../utils/contract'; -import { starkCurve } from '../utils/ec'; import { parseUDCEvent } from '../utils/events'; import { calculateContractAddressFromHash, @@ -55,8 +54,8 @@ import { } from '../utils/hash'; import { toBigInt, toCairoBool } from '../utils/num'; import { parseContract } from '../utils/provider'; -import { estimatedFeeToMaxFee, formatSignature, randomAddress } from '../utils/stark'; -import { getExecuteCalldata } from '../utils/transaction'; +import { estimatedFeeToMaxFee, formatSignature } from '../utils/stark'; +import { buildUDCCall, getExecuteCalldata } from '../utils/transaction'; import { getMessageHash } from '../utils/typedData'; import { AccountInterface } from './interface'; @@ -366,40 +365,7 @@ export class Account extends Provider implements AccountInterface { payload: UniversalDeployerContractPayload | UniversalDeployerContractPayload[], details?: InvocationsDetails | undefined ): Promise { - const params = [].concat(payload as []).map((it) => { - const { - classHash, - salt, - unique = true, - constructorCalldata = [], - } = it as UniversalDeployerContractPayload; - - const compiledConstructorCallData = CallData.compile(constructorCalldata); - const deploySalt = salt ?? randomAddress(); - - return { - call: { - contractAddress: UDC.ADDRESS, - entrypoint: UDC.ENTRYPOINT, - calldata: [ - classHash, - deploySalt, - toCairoBool(unique), - compiledConstructorCallData.length, - ...compiledConstructorCallData, - ], - }, - address: calculateContractAddressFromHash( - unique ? starkCurve.pedersen(this.address, deploySalt) : deploySalt, - classHash, - compiledConstructorCallData, - unique ? UDC.ADDRESS : 0 - ), - }; - }); - - const calls = params.map((it) => it.call); - const addresses = params.map((it) => it.address); + const { calls, addresses } = buildUDCCall(payload, this.address); const invokeResponse = await this.execute(calls, undefined, details); return { diff --git a/src/account/wallet.ts b/src/account/wallet.ts index be7771dcc..02d6b61c7 100644 --- a/src/account/wallet.ts +++ b/src/account/wallet.ts @@ -11,6 +11,7 @@ import { } from 'get-starknet-core'; import { StarknetChainId } from '../constants'; +import { buildUDCCall } from '../utils/transaction'; // eslint-disable-next-line import/no-cycle import { AllowArray, @@ -146,6 +147,11 @@ export class WalletAccount /* implements AccountInterface */ { abi: json.stringify(pContract.abi), }; + // Check FIx + if (!declareContractPayload.compiledClassHash) { + throw Error('compiledClassHash is required'); + } + const rpcCall: RpcCall = { type: 'starknet_addDeclareTransaction', params: { @@ -159,16 +165,23 @@ export class WalletAccount /* implements AccountInterface */ { public async deploy( payload: UniversalDeployerContractPayload | UniversalDeployerContractPayload[] ): Promise { - // TODO: Create UDC PRocedure using invoke() - return new Promise((e) => false); + const { calls, addresses } = buildUDCCall(payload, this.address); + const invokeResponse = await this.execute(calls); + + return { + ...invokeResponse, + contract_address: addresses, + }; } public async deployAccount(payload: DeployAccountContractPayload) { const rpcCall: RpcCall = { type: 'starknet_addDeployAccountTransaction', params: { - contract_address_salt: payload.addressSalt?.toString(), - constructor_calldata: CallData.compile(payload.constructorCalldata), + contract_address_salt: payload.addressSalt?.toString() || '0', + constructor_calldata: payload.constructorCalldata + ? CallData.compile(payload.constructorCalldata) + : [], class_hash: payload.classHash, }, }; diff --git a/src/utils/transaction.ts b/src/utils/transaction.ts index cd3a41b06..003725376 100644 --- a/src/utils/transaction.ts +++ b/src/utils/transaction.ts @@ -1,7 +1,18 @@ -import { BigNumberish, CairoVersion, Call, CallStruct, Calldata, ParsedStruct } from '../types'; +import { UDC } from '../constants'; +import { + BigNumberish, + CairoVersion, + Call, + CallStruct, + Calldata, + ParsedStruct, + UniversalDeployerContractPayload, +} from '../types'; import { CallData } from './calldata'; -import { getSelectorFromName } from './hash'; -import { toBigInt } from './num'; +import { starkCurve } from './ec'; +import { calculateContractAddressFromHash, getSelectorFromName } from './hash'; +import { toBigInt, toCairoBool } from './num'; +import { randomAddress } from './stark'; /** * Transforms a list of Calls, each with their own calldata, into @@ -81,3 +92,45 @@ export const getExecuteCalldata = (calls: Call[], cairoVersion: CairoVersion = ' } return fromCallsToExecuteCalldata(calls); }; + +export function buildUDCCall( + payload: UniversalDeployerContractPayload | UniversalDeployerContractPayload[], + address: string +) { + const params = [].concat(payload as []).map((it) => { + const { + classHash, + salt, + unique = true, + constructorCalldata = [], + } = it as UniversalDeployerContractPayload; + + const compiledConstructorCallData = CallData.compile(constructorCalldata); + const deploySalt = salt ?? randomAddress(); + + return { + call: { + contractAddress: UDC.ADDRESS, + entrypoint: UDC.ENTRYPOINT, + calldata: [ + classHash, + deploySalt, + toCairoBool(unique), + compiledConstructorCallData.length, + ...compiledConstructorCallData, + ], + }, + address: calculateContractAddressFromHash( + unique ? starkCurve.pedersen(address, deploySalt) : deploySalt, + classHash, + compiledConstructorCallData, + unique ? UDC.ADDRESS : 0 + ), + }; + }); + + return { + calls: params.map((it) => it.call), + addresses: params.map((it) => it.address), + }; +}