Beginner

Token rotation

This guide explains how to use token rotation with your modern Slack app. Token rotation provides an extra layer of security for your access tokens.

The first part of the guide covers token rotation for a brand new app. Use this flow if you're building an app from scratch, or if you have a classic Slack app and you would rather make a new app with granular permissions rather than migrate your app.

The second part of the guide covers token rotation for a modern, existing Slack app that already uses granular permissions. You'll learn how to exchange your access tokens for a refresh token and expiring access token.

Read on to get started.

Overview

Token rotation is defined by the OAuth V2 RFC. Instead of an access token representing an existing installation of your Slack app indefinitely, the access token expires. A refresh token acts as a long-lived way to refresh your access tokens.

For Slack apps, the access token types that may be refreshed are granular bot or user tokens.


Get started with a new app

This section covers setting up token rotation for a new app. If you've got an existing, modern app—installed using the new version of OAuth V2—skip to the migration section.

If you've never developed a Slack app before, take a look at our overview of Slack's OAuth V2 flow. You'll want to know how to implement OAuth before you turn on token rotation.

Create a new app

If you haven't already, create a new Slack app with our easygoing UI:

Create a new Slack app

Fill out your App Name and select the Development Workspace where you'll play around and build your app. Don't fuss too much over either field—no matter what workspace you select, you'll still be able to distribute your app to other workspaces if you choose.

Consider SDKs

If you use Bolt to develop your app, your job will be a whole lot easier. Token rotation is automatically handled in the Bolt frameworks for building Slack apps with JS and Python. Just be sure to use the version that supports token rotation. For example:

# Node
npm i @slack/bolt@3.5

# Python
pip install "slack-bolt>=1.7"

# Java
implementation("com.slack.api:bolt-jetty:1.9.+")

Then turn on token rotation.

If you've decided to develop your own app without Bolt, continue through the rest of this guide.

Turn on token rotation

Token rotation is enabled for your app via the OAuth & Permissions section in the sidebar of your app config.

Warning: token rotation may not be turned off once it's turned on. You'll want to be sure you're prepared to refresh your token within 12 hours before you turn on the toggle.

Expect a modified oauth.v2.access response

Any time you implement OAuth with your Slack app, whether token rotation is enabled or not, the last step of the flow requires you to call the oauth.v2.access method to exchange your temporary code for an access token.

When you have turned on the token rotation toggle, your app will receive additional data from oauth.v2.access. Expect a response that contains the following new fields:

    ...
    "expires_in": 43200, // 12 hours
    "refresh_token": "xoxe-1-...",
    ...

If you make use of a user token, expect those two new fields along with your access token in the authed_user object of the response:


    "authed_user": {
        "id": "U1234",
        "scope": "chat:write",
        "access_token": "xoxe.xoxp-1-1234-...",
        "expires_in": 43200, // 12 hours
        "refresh_token": "xoxe-1-..."
        "token_type": "user"
    }

You can receive refresh tokens for both user tokens and bot tokens in the same oauth.v2.access response.

The expires_in field defines the number of seconds until the access token you've received expires.

Store the refresh token as you would an access token, in a database or secure datastore (not in code).

Additionally, you'll probably notice that your access_token now has a new xoxe. prefix.

Refresh a token

Schedule a task to refresh your token before the expires_in time. If you don't refresh your access token in time, you'll receive an error when you make an API call with the expired token.

It's strongly suggested that you refresh your token before it expires, rather than waiting for it to expire and checking for an error from the Slack API.

In order to refresh a token, make another call to oauth.v2.access, this time supplying your refresh token from above along with a new grant_type parameter:

POST /api/oauth.v2.access
HOST slack.com
Content-Type: application/x-www-form-urlencoded

client_id=60503450.61416
client_secret=8bc5fc53901afc11c
grant_type=refresh_token
refresh_token=xoxe-1-...

Note that client_id and client_secret are still required for this call to oauth.v2.access.

Expect responses from this new call to oauth.v2.access that are exactly like those above.

Once you've successfully refreshed a token, congratulations! You're now developing with a more secure app that makes use of token rotation.


Migrate an existing app to use token rotation

This section covers setting up token rotation for an existing, modern Slack app. If you're making an app from scratch or don't have an app that's installed using the new version of OAuth V2, head back to the section for new apps.

Test with a development app

Before you turn on token rotation, consider how you're going to test your implementation. You don't want all your access tokens to expire before you've successfully figured out how to refresh them.

If your app is listed in the app directory, now is a good time to follow the advice in our guide to testing directory apps. Hint: a development or staging app is an important part of testing changes before they go to production.

If you use Bolt in JS or Python, you're already good to go with token rotation, as long as you're using the beta versions that support token rotation:

# Node
npm i @slack/bolt@3.5

# Python
pip install "slack-bolt>=1.7"

# Java
implementation("com.slack.api:bolt-jetty:1.9.+")

Turn on token rotation

Turn on token rotation in your app config. You'll be able to opt-in by navigating to the OAuth & Permissions sidebar of the config.

Warning: token rotation may not be turned off once it's turned on. You'll want to be sure you're prepared to refresh your token within 12 hours before you turn on the toggle. Test your app in a development environment before enabling token rotation in production.

Call oauth.v2.exchange to gain a refresh token and expiring access token

Once you've enabled token rotation, you'll still need to call the oauth.v2.exchange method to exchange your long-lived access token for a refresh token and an expiring access token.

Here's a sample call:

POST /api/oauth.v2.exchange
HOST slack.com
Content-Type: application/x-www-form-urlencoded

client_id=60503450.61416
client_secret=8bc5fc53901afc11c
token=xoxb-1234-...

Either a granular bot token or user token may be exchanged for a refresh token and expiring access token. You won't be able to exchange the same access token for a refresh token more than once.

The original access token, once exchanged for a rotating token and expiring token, will no longer function—as soon as you use your new tokens for the first time.

Here's a sample response from oauth.v2.exchange when exchanging a bot token:

{
    "ok": true,
    "access_token": "xoxe.xoxb-1-...", // New access token
    "expires_in": 43200, // 12 hours
    "refresh_token": "xoxe-1-...", // New refresh token
    "token_type": "bot",
    "scope": "commands,incoming-webhook",
    "bot_user_id": "U0KRQLJ9H",
    "app_id": "A0KRD7HC3",
    "team": {
        "name": "Slack Softball Team",
        "id": "T9TK3CUKW"
    },
    "enterprise": {
        "name": "slack-sports",
        "id": "E12345678"
    },
}

Refresh a token

Now that you've opted in and obtained a refresh token, your flow is the same as the one for new apps.

Refresh your token before the expires_in parameter tells you that your access token expires by calling the oauth.v2.access method, supplying the refresh_token parameter and setting grant_type to refresh_token:

POST /api/oauth.v2.access
HOST slack.com
Content-Type: application/x-www-form-urlencoded

client_id=60503450.61416
client_secret=8bc5fc53901afc11c
grant_type=refresh_token
refresh_token=xoxe-1-...

Note that client_id and client_secret are still required for this call to oauth.v2.access.

After you've successfully refreshed a token, congratulations! Your app has landed in the new, safer world of token rotation.


App manifests and token rotation

You may also create a new app that makes use of token rotation using app manifests.

Add the following to your app manifest YAML to enable token rotation:

settings:
  token_rotation_enabled: true

Uninstalling apps

Slack APIs provide multiple ways to undo Slack installations. With apps.uninstall, behavior is the same regardless of whether the app uses token rotation. The app is uninstalled and all tokens associated with the installation are revoked.

auth.revoke is used to revoke a single token of an installation. When used on an app without token rotation, it usually revokes the authorization associated with it, meaning that the user or team that had the app installed needs to reinstall it.

If the app has token rotation turned on, auth.revoke will revoke a single token (a refresh token, a bot access token that expires, or a user access token that expires) without changing the underlying installation. Events will still be delivered and new tokens may still be generated in the UI.

Recommended reading
Next steps

Was this page helpful?