<VersionWarning version="0.1" />

# How to send multiple user operations in parallel

permissionless.js library lets you to send multiple transactions in parallel. This can be useful if you want to batch multiple calls in a single user operation or if you want to send user operations concurrently.

## Batching Multiple Calls

To batch multiple calls in a single user operation, you can use the `sendTransactions` method.

```ts
const trasnactionHash = await smartAccountClient.sendTransactions({
	transactions: [
		{
			to: "0xd8da6bf26964af9d7eed9e03e53415d37aa96045",
			value: parseEther("0.1"),
			data: "0x",
		},
		{
			to: "0xd8da6bf26964af9d7eed9e03e53415d37aa96045",
			value: parseEther("0.1"),
			data: "0x",
		},
	],
})
```

## Sending Multiple User Operations in Parallel

In an Externally Owned Account (EOA), the `nonce` is a simple incrementing number. However, in smart accounts, the `nonce` consists of two components: a `key` and a `sequence`:

* 192-bit “key”
* 64-bit “sequence”

For each unique `key`, the sequence must be incremented by 1 for each transaction. This means that if you send multiple transactions in parallel, you can use different `keys` for the parallel transactions.

### Parallel Transactions Ordering

Important thing to note is that parallel transaction's ordering is not guaranteed. So execution of random `key` on chain could be:

* \[key-C]\[sequence-0]
* \[key-A]\[sequence-0]
* \[key-B]\[sequence-0]

While execution of `sequence` for a specific `key` will always be in order. So the following is a valid order of execution:

1. \[key-C]\[sequence-0]
2. \[key-A]\[sequence-0]
3. \[key-C]\[sequence-1]
4. \[key-B]\[sequence-0]
5. \[key-A]\[sequence-1]
6. \[key-B]\[sequence-1]

:::info
Note: Pimlico bundler currently only support up to 100 parallel transactions. If you need to send more than 100 transactions in parallel feel free to contact us at [support@pimlico.io](mailto\:support@pimlico.io).
:::

In the example below, we use the current timestamp as the `key` to send parallel transactions. You can use any other value as the `key`.

```ts
import { encodeNonce } from "permissionless/utils"

const parallelNonce1 = encodeNonce({
	key: BigInt(Date.now()),
	sequence: 0n,
})

const transaction1 = smartAccountClient.sendTransactions({
	transactions: [
		{
			to: "0xd8da6bf26964af9d7eed9e03e53415d37aa96045",
			value: parseEther("0.1"),
			data: "0x",
		},
		{
			to: "0xd8da6bf26964af9d7eed9e03e53415d37aa96045",
			value: parseEther("0.1"),
			data: "0x",
		},
	],
	nonce: parallelNonce1,
})

const parallelNonce2 = encodeNonce({
	key: BigInt(Date.now()),
	sequence: 0n,
})

const transaction2 = smartAccountClient.sendTransactions({
	transactions: [
		{
			to: "0xd8da6bf26964af9d7eed9e03e53415d37aa96045",
			value: parseEther("0.1"),
			data: "0x",
		},
		{
			to: "0xd8da6bf26964af9d7eed9e03e53415d37aa96045",
			value: parseEther("0.1"),
			data: "0x",
		},
	],
	nonce: parallelNonce2,
})

const hashes = await Promise.all([transaction1, transaction2])
```

This way, you can efficiently manage multiple transactions either sequentially or concurrently.
