Build a custom flow for handling user impersonation
Warning
This guide is for users who want to build a custom user interface using the Clerk API. To use a prebuilt UI, use the Account Portal pages or prebuilt components.
User impersonation is a way to offer customer support by logging into your application from their accounts. Doing so enables you to directly reproduce and remedy any issues they're experiencing.
This guide will walk you through how to build a custom flow that handles user impersonation.
Next.js
Expo
The following example builds a dashboard that is only accessible to users with the admin:impersonatepermission. You can modify the authorization checks to fit your use case.
In the dashboard, the user will see a list of the application's users. When the user chooses to impersonate a user, they will be signed in as that user and redirected to the homepage.
Use the following tabs to view the code for:
The main page that gets the list of the application's users using the JavaScript Backend SDK
The Client Component that has the UI for displaying the users and the ability to impersonate them
The Server Action that generates the actor token using the Backend API
This example uses expo-router's experimental API routes for simplicity. However, you can use your own backend server to handle the API routes.
To use Expo's experimental API routes, you must follow the Expo deployment docs. Doing so allows your impersonation endpoints to access to your CLERK_SECRET_KEY.
It is recommended that you should build impersonation into an admin-only dashboard that only authorized users can access.
The person visiting this dashboard should not be able to see it unless signed in. To protect the dashboard, create the dashboard route group with a layout that redirects users if they're already signed in, as shown in the following example:
Create the main page of the dashboard, which will hold most of your impersonation code. This example contains the skeleton of the final result, which will be fleshed out with each step in this guide. To skip the step-by-step process, see the full example at the end of this guide.
Now create an endpoint that will call the create actor token endpoint at /actor_tokens and pass in the Clerk secret key for authorization. In your API, you should build in permission checks to make sure this is only being accessed from a trusted source.
Create a second custom hook called useImpersonatedUser() that will fetch data about the impersonator. You can use this to display UI only the impersonator will see for specific actions, like showing who is currently impersonating and matching the session to the right user for logout.
With your hook setup you can now create an API route that will call the retrieve user endpoint at /users and get back the Impersonated user's full Userobject.
Now that you have the functionality for generating an impersonated session & getting the impersonated user's data, there are a few more functions to complete that will:
Get the ticket from the URL generated by your useImpersonation() hook.
Pass the ticket to the signIn() function to create a new impersonated session, allowing you to sign in the impersonated user or impersonator.
The following code should be placed in the Page component of your app/(dashboard)/index.tsx file:
Finally, create a helper function for signing out. Usually this can be as simple as calling the signOut() function, but since you're handling multiple sessions, you must add some checks to ensure you're signing out of the right session.