# MetaMask Smart Accounts API reference

> MetaMask Smart Accounts-related API methods reference.

# MetaMask Smart Accounts API reference

The following API methods are related to creating, managing, and signing with [MetaMask Smart Accounts](../concepts/smart-accounts.md).

## `aggregateSignature`

Aggregates multiple partial signatures into a single combined multisig signature.

### Parameters

| Name         | Type                                                | Required | Description                                                                                      |
| ------------ | --------------------------------------------------- | -------- | ------------------------------------------------------------------------------------------------ |
| `signatures` | [`PartialSignature`](./types.md#partialsignature)[] | Yes      | Collection of partial signatures provided by signers, to be merged into an aggregated signature. |

### Example

<Tabs>
<TabItem value="example.ts">

```typescript

  bundlerClient,
  aliceSmartAccount,
  bobSmartAccount,
  aliceAccount,
  bobAccount,
} from './config.ts'

const userOperation = await bundlerClient.prepareUserOperation({
  account: aliceSmartAccount,
  calls: [
    {
      target: zeroAddress,
      value: 0n,
      data: '0x',
    },
  ],
})

const aliceSignature = await aliceSmartAccount.signUserOperation(userOperation)
const bobSignature = await bobSmartAccount.signUserOperation(userOperation)

const aggregatedSignature = aggregateSignature({
  signatures: [
    {
      signer: aliceAccount.address,
      signature: aliceSignature,
      type: 'ECDSA',
    },
    {
      signer: bobAccount.address,
      signature: bobSignature,
      type: 'ECDSA',
    },
  ],
})
```

</TabItem>
<TabItem value="config.ts">

```typescript

const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const alicePrivateKey = generatePrivateKey()
const aliceAccount = privateKeyToAccount(alicePrivateKey)

const bobPrivateKey = generatePrivateKey()
const bobAccount = privateKeyToAccount(bobPrivateKey)

const signers = [aliceAccount.address, bobAccount.address]
const threshold = 2n

export const aliceSmartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.MultiSig,
  deployParams: [signers, threshold],
  deploySalt: '0x',
  signer: [{ account: aliceAccount }],
})

export const bobSmartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.MultiSig,
  deployParams: [signers, threshold],
  deploySalt: '0x',
  signer: [{ account: bobAccount }],
})

export const bundlerClient = createBundlerClient({
  client: publicClient,
  transport: http('https://public.pimlico.io/v2/rpc'),
})
```

</TabItem>
</Tabs>

## `encodeCalls`

Encodes calls for execution by a MetaMask smart account. If there's a single call directly to the smart account, it returns the call data directly. For multiple calls or calls to other addresses, it creates executions and encodes them for the smart account's `execute` function.

The execution mode is set to `SingleDefault` for a single call to other address, or `BatchDefault` for multiple calls.

### Parameters

| Name    | Type     | Required | Description                  |
| ------- | -------- | -------- | ---------------------------- |
| `calls` | `Call[]` | Yes      | List of calls to be encoded. |

### Example

<Tabs>
<TabItem value ="example.ts">

```ts

const calls = [
  {
    to: zeroAddress,
    data: '0x',
    value: 0n,
  },
]

const executeCallData = await smartAccount.encodeCalls(calls)
```

</TabItem>

<TabItem value ="config.ts">

```ts

const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const delegatorAccount = privateKeyToAccount('0x...')

export const smartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Hybrid,
  deployParams: [delegatorAccount.address, [], [], []],
  deploySalt: '0x',
  signer: { account: delegatorAccount },
})
```

</TabItem>
</Tabs>

## `getFactoryArgs`

Returns the factory address and factory data that can be used to deploy a smart account.

### Example

<Tabs>
<TabItem value ="example.ts">

```ts

const { factory, factoryData } = await smartAccount.getFactoryArgs()
```

</TabItem>

<TabItem value ="config.ts">

```ts

const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const delegatorAccount = privateKeyToAccount('0x...')

export const smartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Hybrid,
  deployParams: [delegatorAccount.address, [], [], []],
  deploySalt: '0x',
  signer: { account: delegatorAccount },
})
```

</TabItem>
</Tabs>

## `getNonce`

Returns the nonce for a smart account.

### Parameters

| Name  | Type     | Required | Description                                                                                                                           |
| ----- | -------- | -------- | ------------------------------------------------------------------------------------------------------------------------------------- |
| `key` | `bigint` | No       | The nonce key to retrieve the nonce. Different keys maintain independent nonce sequences, enabling parallel user operation execution. |

### Example

<Tabs>
<TabItem value ="example.ts">

```ts

const nonce = await smartAccount.getNonce()
```

</TabItem>

<TabItem value ="config.ts">

```ts

const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const delegatorAccount = privateKeyToAccount('0x...')

export const smartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Hybrid,
  deployParams: [delegatorAccount.address, [], [], []],
  deploySalt: '0x',
  signer: { account: delegatorAccount },
})
```

</TabItem>
</Tabs>

## `signDelegation`

Signs the delegation and returns the delegation signature.

### Parameters

| Name         | Type                            | Required | Description                                               |
| ------------ | ------------------------------- | -------- | --------------------------------------------------------- |
| `delegation` | `Omit<Delegation, "signature">` | Yes      | The unsigned delegation object to sign.                   |
| `chainId`    | `number`                        | No       | The chain ID on which the Delegation Manager is deployed. |

### Example

<Tabs>
<TabItem value ="example.ts">

```ts

  createDelegation,
  getSmartAccountsEnvironment,
  ScopeType,
} from '@metamask/smart-accounts-kit'

// The address to which the delegation is granted. It can be an EOA address, or
// smart account address.
const delegate = '0x2FcB88EC2359fA635566E66415D31dD381CF5585'

const delegation = createDelegation({
  to: delegate,
  from: account.address,
  environment: delegatorSmartAccount.environment,
  scope: {
    type: ScopeType.NativeTokenTransferAmount,
    // 0.001 ETH in wei format.
    maxAmount: 1000000000000000n,
  },
})

const signature = delegatorSmartAccount.signDelegation({ delegation })
```

</TabItem>
<TabItem value ="config.ts">

```ts

const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const delegatorAccount = privateKeyToAccount('0x...')

export const delegatorSmartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Hybrid,
  deployParams: [delegatorAccount.address, [], [], []],
  deploySalt: '0x',
  signer: { account: delegatorAccount },
})
```

</TabItem>
</Tabs>

## `signMessage`

Generates the [EIP-191](https://eips.ethereum.org/EIPS/eip-191) signature
using the `MetaMaskSmartAccount` signer. The Smart Accounts Kit
uses Viem under the hood to provide this functionality.

### Parameters

See the [Viem `signMessage` parameters](https://viem.sh/account-abstraction/accounts/smart/signMessage).

### Example

<Tabs>
<TabItem value ="example.ts">

```ts

const signature = smartAccount.signMessage({
  message: 'hello world',
})
```

</TabItem>
<TabItem value ="config.ts">

```ts

const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const account = privateKeyToAccount('0x...')

export const smartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Hybrid,
  deployParams: [account.address, [], [], []],
  deploySalt: '0x',
  signer: { account },
})
```

</TabItem>
</Tabs>

## `signTypedData`

Generates the [EIP-712](https://eips.ethereum.org/EIPS/eip-712) signature
using the `MetaMaskSmartAccount` signer. The Smart Accounts Kit
uses Viem under the hood to provide this functionality.

### Parameters

See the [Viem `signTypedData` parameters](https://viem.sh/account-abstraction/accounts/smart/signTypedData).

### Example

<Tabs>
<TabItem value ="example.ts">

```ts

const signature = smartAccount.signTypedData({
  domain,
  types,
  primaryType: 'Mail',
  message: {
    from: {
      name: 'Cow',
      wallet: '0xCD2a3d9F938E13CD947Ec05AbC7FE734Df8DD826',
    },
    to: {
      name: 'Bob',
      wallet: '0xbBbBBBBbbBBBbbbBbbBbbbbBBbBbbbbBbBbbBBbB',
    },
    contents: 'Hello, Bob!',
  },
})
```

</TabItem>
<TabItem value ="config.ts">

```ts

const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const account = privateKeyToAccount('0x...')

export const smartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Hybrid,
  deployParams: [account.address, [], [], []],
  deploySalt: '0x',
  signer: { account },
})
```

</TabItem>
</Tabs>

## `signUserOperation`

Signs a <GlossaryTerm term="User operation">user operation</GlossaryTerm> with the `MetaMaskSmartAccount` signer. The Delegation
Toolkit uses Viem under the hood to provide this functionality.

### Parameters

See the [Viem `signUserOperation` parameters](https://viem.sh/account-abstraction/accounts/smart/signUserOperation#parameters).

### Example

<Tabs>
<TabItem value ="example.ts">

```ts

const userOpSignature = smartAccount.signUserOperation({
  callData: '0xdeadbeef',
  callGasLimit: 141653n,
  maxFeePerGas: 15000000000n,
  maxPriorityFeePerGas: 2000000000n,
  nonce: 0n,
  preVerificationGas: 53438n,
  sender: '0xE911628bF8428C23f179a07b081325cAe376DE1f',
  verificationGasLimit: 259350n,
  signature: '0x',
})
```

</TabItem>
<TabItem value ="config.ts">

```ts

const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const account = privateKeyToAccount('0x...')

export const smartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Hybrid,
  deployParams: [account.address, [], [], []],
  deploySalt: '0x',
  signer: { account },
})
```

</TabItem>
</Tabs>

## `toMetaMaskSmartAccount`

Creates a `MetaMaskSmartAccount` instance.

### Parameters

| Name              | Type                                                              | Required                                                                                                   | Description                                                                                                                                                                                                                                                                                                                                   |
| ----------------- | ----------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `client`          | `Client`                                                          | Yes                                                                                                        | Viem Client to retrieve smart account data.                                                                                                                                                                                                                                                                                                   |
| `implementation`  | `TImplementation`                                                 | Yes                                                                                                        | Implementation type for the smart account. Can be <GlossaryTerm term="Hybrid smart account">`Hybrid`</GlossaryTerm>, <GlossaryTerm term="Multisig smart account">`Multisig`</GlossaryTerm>, or <GlossaryTerm term="EIP-7702 smart account">`Stateless7702`</GlossaryTerm>.                                                                    |
| `signer`          | `SignerConfigByImplementation <TImplementation>`                  | No                                                                                                         | Signer for the smart account. Can be a Viem Account, Viem Wallet Client, or a WebAuthn Account. WebAuthn accounts are only supported for Hybrid implementations. If omitted, non-signing operations still work, but signing operations such as `signUserOperation`, `signDelegation`, `signMessage`, and `signTypedData` will throw an error. |
| `environment`     | [`SmartAccountsEnvironment`](./types.md#smartaccountsenvironment) | No                                                                                                         | Environment to resolve the smart contracts.                                                                                                                                                                                                                                                                                                   |
| `deployParams`    | `DeployParams<TImplementation>`                                   | Required if `address` is not provided                                                                      | The parameters that will be used to deploy the smart account and generate its deterministic address.                                                                                                                                                                                                                                          |
| `deploySalt`      | `Hex`                                                             | Required if `address` is not provided                                                                      | The salt that will be used to deploy the smart account.                                                                                                                                                                                                                                                                                       |
| `address`         | `Address`                                                         | Required if `deployParams` and `deploySalt` are not provided, or if the implementation is `Stateless7702`. | The address of the smart account. If an address is provided, the smart account will not be deployed. This should be used if you intend to interact with an existing smart account.                                                                                                                                                            |
| `nonceKeyManager` | `NonceManager`                                                    | No                                                                                                         | A custom nonce key manager for managing nonces. If provided, it enables support for multiple nonce keys to avoid collisions during parallel user operation execution.                                                                                                                                                                         |

### Hybrid implementation

#### `deployParams`

All Hybrid deploy parameters are required:

| Name          | Type       | Description                                                                                                   |
| ------------- | ---------- | ------------------------------------------------------------------------------------------------------------- |
| `owner`       | `Hex`      | The owner's account address. The owner can be the zero address, indicating that there is no owner configured. |
| `p256KeyIds`  | `Hex[]`    | An array of key identifiers for passkey signers.                                                              |
| `p256XValues` | `bigint[]` | An array of public key x-values for passkey signers.                                                          |
| `p256YValues` | `bigint[]` | An array of public key y-values for passkey signers.                                                          |

#### Example

<Tabs>
<TabItem value ="example.ts">

```ts

const smartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Hybrid,
  deployParams: [account.address, [], [], []],
  deploySalt: '0x',
  signer: { account: account },
})
```

</TabItem>
<TabItem value ="config.ts">

```ts

export const account = privateKeyToAccount('0x...')
export const publicClient = createPublicClient({
  chain,
  transport: http(),
})
```

</TabItem>
</Tabs>

### Multisig implementation

#### `deployParams`

All Multisig deploy parameters are required:

| Name        | Type     | Description                                              |
| ----------- | -------- | -------------------------------------------------------- |
| `signers`   | `Hex[]`  | An array of EOA signer addresses.                        |
| `threshold` | `bigint` | The number of signers required to execute a transaction. |

#### Example

<Tabs>
<TabItem value="example.ts">

```ts

const signers = [aliceAccount.address, bobAccount.address]
const threshold = 2n

const aliceSmartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.MultiSig,
  deployParams: [signers, threshold],
  deploySalt: '0x',
  signer: [{ account: aliceAccount }],
})
```

</TabItem>
<TabItem value="config.ts">

```ts

export const publicClient = createPublicClient({
  chain,
  transport: http(),
})

const alicePrivateKey = generatePrivateKey()
export const aliceAccount = privateKeyToAccount(alicePrivateKey)

const bobPrivateKey = generatePrivateKey()
export const bobAccount = privateKeyToAccount(bobPrivateKey)
```

</TabItem>
</Tabs>

### Stateless7702 implementation example

<Tabs>
<TabItem value ="example.ts">

```ts

const smartAccount = await toMetaMaskSmartAccount({
  client: publicClient,
  implementation: Implementation.Stateless7702,
  address: account.address,
  signer: { account },
})
```

</TabItem>
<TabItem value ="config.ts">

```ts

export const account = privateKeyToAccount('0x...')
export const publicClient = createPublicClient({
  chain,
  transport: http(),
})
```

</TabItem>
</Tabs>
