***

## description: Grant and revoke TIP-20 roles, cap supply, and pause transfers on Tempo.

# Manage Token Roles & Supply

## Overview

TIP-20 tokens use role-based access control. The admin grants roles like issuer (mint and burn),
configures which role administers each role, caps the maximum supply, and can pause all transfers in
an emergency. These controls let an issuer operate a token safely as it grows.

[See the TIP-20 role-based access control specification](https://docs.tempo.xyz/protocol/tip20/spec#role-based-access-control)

## Recipes

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

### Grant and Revoke Roles

Grant a role with [`token.grantRolesSync`](/tempo/actions/token.grantRoles) and remove it with
[`token.revokeRolesSync`](/tempo/actions/token.revokeRoles). The issuer role is required to mint and
burn supply.

:::code-group

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

const { value } = await client.token.grantRolesSync({
  roles: ['issuer'],
  to: '0x742d35Cc6634C0532925a3b844Bc9e7595f0bEbb',
  token: '0x20c0000000000000000000000000000000000000',
})
```

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

:::

### Check and Renounce a Role

Check whether an account holds a role with [`token.hasRole`](/tempo/actions/token.hasRole). An
account can voluntarily give up its own role with
[`token.renounceRolesSync`](/tempo/actions/token.renounceRoles).

:::code-group

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

const hasRole = await client.token.hasRole({
  account: '0x742d35Cc6634C0532925a3b844Bc9e7595f0bEbb',
  role: 'issuer',
  token: '0x20c0000000000000000000000000000000000000',
})
```

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

:::

### Set the Admin of a Role

Control which role can grant and revoke another role with
[`token.setRoleAdminSync`](/tempo/actions/token.setRoleAdmin). This lets you delegate management of,
for example, the issuer role to a dedicated operations role.

:::code-group

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

const { receipt } = await client.token.setRoleAdminSync({
  adminRole: 'defaultAdmin',
  role: 'issuer',
  token: '0x20c0000000000000000000000000000000000000',
})
```

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

:::

### Cap the Total Supply

Set a hard ceiling on how many tokens can ever exist with
[`token.setSupplyCapSync`](/tempo/actions/token.setSupplyCap). Mints that would exceed the cap revert.

:::code-group

```ts twoslash [example.ts]
import { parseUnits } from 'viem'
import { client } from './viem.config'

const { newSupplyCap } = await client.token.setSupplyCapSync({
  supplyCap: parseUnits('1000000', 6),
  token: '0x20c0000000000000000000000000000000000000',
})
```

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

:::

### Pause and Unpause Transfers

In an emergency, halt all transfers with [`token.pauseSync`](/tempo/actions/token.pause) and resume
them with [`token.unpauseSync`](/tempo/actions/token.unpause).

:::code-group

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

const { isPaused } = await client.token.pauseSync({
  token: '0x20c0000000000000000000000000000000000000',
})
```

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

:::

## Best Practices

### Grant the Least Privilege Needed

Give each operator only the roles required for its job. Keep the admin role on a secured account and
grant the issuer role to the systems that actually mint, so a compromised issuer cannot change roles.

### Treat Pausing as a Break-Glass Control

Pausing stops every transfer of the token, including legitimate user activity. Use it only for
incident response, and have a clear process to unpause once the issue is resolved.

### Set a Supply Cap Early

Configuring a supply cap before wide distribution gives holders a credible guarantee about maximum
issuance. Raising it later is possible but undermines that guarantee, so choose the value carefully.

## See More

<Cards>
  <Card icon="lucide:flame" title="Mint & Burn Tokens" description="Use the issuer role to mint and burn supply." to="/tempo/guides/manage-token-balances" />

  <Card icon="lucide:shield-check" title="Configure Transfer Policies" description="Restrict which accounts can send or receive the token." to="/tempo/guides/transfer-policies" />

  <Card icon="lucide:square-function" title="token.grantRoles" description="Grant TIP-20 roles such as issuer." to="/tempo/actions/token.grantRoles" />

  <Card icon="lucide:book-open" title="Tempo Docs: Access Control" description="How TIP-20 role-based access control works." to="https://docs.tempo.xyz/protocol/tip20/spec#role-based-access-control" />
</Cards>
