# Concurrent Transactions

## Overview

Tempo's concurrent nonce system lets a single account send multiple transactions in parallel,
without waiting for each one to confirm sequentially. By using different nonce keys, transactions
that don't conflict can execute simultaneously, significantly improving throughput for
high-activity accounts.

[See the Tempo Transactions specification](https://docs.tempo.xyz/protocol/transactions/spec-tempo-transaction)

## Recipes

These recipes assume you have [set up a Tempo client](/tempo).

### Send in Parallel

Submit multiple transactions at once with `Promise.all`. Viem assigns non-conflicting nonce keys
automatically.

:::code-group
```ts twoslash [example.ts]
import { client } from './viem.config'

const [receipt1, receipt2] = await Promise.all([
  client.sendTransactionSync({
    data: '0xcafebabe00000000000000000000000000000001',
    to: '0xdeadbeefdeadbeefdeadbeefdeadbeefdeadbeef',
  }),
  client.sendTransactionSync({
    data: '0xdeadbeef00000000000000000000000000000002',
    to: '0xfeedfacefeedfacefeedfacefeedfacefeedface',
  }),
])
```

```ts twoslash [viem.config.ts] filename="viem.config.ts"
// [!include ~/snippets/tempo/viem.config.ts:setup]
```
:::

### Control Nonce Keys

For finer control, assign each transaction a distinct `nonceKey` so they cannot conflict. Nonce
keys must be greater than `0` (key `0` is reserved for protocol nonces).

:::code-group
```ts twoslash [example.ts]
import { client } from './viem.config'

const hash1 = await client.sendTransaction({
  data: '0xcafebabe00000000000000000000000000000001',
  nonceKey: 567n, // [!code focus]
  to: '0xdeadbeefdeadbeefdeadbeefdeadbeefdeadbeef',
})
const hash2 = await client.sendTransaction({
  data: '0xdeadbeef00000000000000000000000000000002',
  nonceKey: 789n, // [!code focus]
  to: '0xfeedfacefeedfacefeedfacefeedfacefeedface',
})
```

```ts twoslash [viem.config.ts] filename="viem.config.ts"
// [!include ~/snippets/tempo/viem.config.ts:setup]
```
:::

### Read a Nonce

Read the current nonce for an account and nonce key with
[`nonce.getNonce`](/tempo/actions/nonce.getNonce).

:::code-group
```ts twoslash [example.ts]
import { client } from './viem.config'

const nonce = await client.nonce.getNonce({
  account: '0xcafebabecafebabecafebabecafebabecafebabe',
  nonceKey: 567n,
})
```

```ts twoslash [viem.config.ts] filename="viem.config.ts"
// [!include ~/snippets/tempo/viem.config.ts:setup]
```
:::

## Best Practices

### Use Distinct Nonce Keys per Stream

Give each independent stream of transactions its own `nonceKey`. Transactions that share a nonce
key are still ordered relative to each other, so reuse a key only when ordering matters and use
separate keys to maximize parallelism.

## See More

<Cards>
  <Card icon="lucide:send" title="Tempo Transactions" description="Send Tempo Transactions and discover the payment features they unlock." to="/tempo/transactions" />

  <Card icon="lucide:square-function" title="nonce.getNonce" description="Read the current nonce for an account and nonce key." to="/tempo/actions/nonce.getNonce" />

  <Card icon="lucide:book-open" title="Tempo Docs: Parallel Transactions" description="The full guide to sending parallel transactions on Tempo." to="https://docs.tempo.xyz/guide/payments/send-parallel-transactions" />
</Cards>
