Building a Custom User Profile with Clerk
- Category
- Guides
- Published
Authentication is one of the most critical functions of securing your applications; however, it's also one of the most challenging functions to implement.
Failing to implement a proper authentication system can make your application vulnerable and your users' information open to potential hackers.
If you don't want to get into the technicalities of implementing an authentication system from scratch, Clerk is your solution. Clerk provides built-in components for your application that can be easily integrated into your frontend application, and it supports most of the popular frameworks, like React, Next.js, and Gatsby.
Clerk can be beneficial for your customer identity management. You can easily manage your user sessions, devices, and profiles from the Clerk dashboard. Moreover, you can easily integrate Clerk with services like Firebase or Google Analytics.
In addition, Clerk makes integrating authentication to your existing application simple since it provides built-in hooks for adding authentication. You can implement social sign-in, password-based authentication, or Web3 logins easily using Clerk. You can also extend your functionalities and create custom components and user profiles using their SDK and APIs.
In this article, you'll see how Clerk authentication can be implemented in your Next.js application and how you can implement the Clerk built-in components for user profiles. You'll also learn how to create custom user profiles for your users and update users' profiles using your custom components.
What Is Clerk?
Clerk is an all-in-one solution for your authentication and user management needs. It provides features like password-based or social sign-in, passwordless login using magic links or email, and SMS passcodes. It also provides a user management dashboard, user analytics, allow/block list, rate limiting, and more.
With Clerk, you can set up a complete user management system within ten minutes. Clerk can seamlessly integrate with popular technologies, including React, Next.js, Gatsby, RedwoodJS, Remix, Node.js, and Go.
For popular frontend frameworks, like React, Remix, RedwoodJS, or Gatsby, Clerk has created well-designed components for login, sign-up, the user profile, and the user button. However, it's not limited to built-in components. You can always create custom components with the help of hooks provided by the Clerk SDK.
Because Clerk provides you with frontend SDK, API, and backend APIs for developing custom pages for your users, building a customer user profile is easy.
Building a Custom User Profile Using Clerk
This article aims to show how you can create custom user profiles for your Next.js applications and how to implement the built-in components. To do this, you'll use the Clerk SDK for Next.js.
The basic flow of the application is shown in the following GIF:
Prerequisites
Before you build your custom user profiles with Clerk, you need to satisfy a few prerequisites, including the following:
- Create a Clerk account.
- Have a basic understanding of Next.js. To learn more about Next.js, you can check out their documentation.
- Have a basic understanding of Tailwind CSS (optional)
You can create a free account for Clerk from the Clerk sign-up page. After creating your account, you'll be redirected to the Clerk dashboard. There, you will be asked to create a new application. Add an application with the name of your choice. This is what the setup for this tutorial looks like:
After successfully creating the application, you'll be able to visit the application's dashboard:
You can find your API keys in the menu under the Developers section. Click on API Keys and copy the frontend API key. You'll need this later in the project.
In addition to your Clerk account, Node.js and npm must be installed on your local computer to create and run the application.
If you want to copy the code and follow along, you can use this GitHub repo.
Creating a Next.js Application
The first step in building this application is to create a Next.js application. To scaffold a Next.js application, run the following command in the terminal:
Once the installation is complete, you can run the application using npm run dev
in the terminal, and the application will start on port 3000
. Next.js will render the index.jsx
file inside the pages
folder. You can delete the contents of the index.jsx
file as it will be customized.
The second step is to integrate Tailwind CSS with your Next.js application. You can follow this Tailwind CSS installation guide to do so.
Then install the Clerk SDK for the Next.js plug-in. To install the SDK, run the following command in the terminal:
For using forms effortlessly, you can also integrate the react-hook-form
plug-in by running the following command:
Another plug-in called react-icons
is used for adding icons to the application. You can install react-icons
by simply running the following command in your terminal:
These previous plug-ins are the only ones that will be used in this application.
Integrating User Profile in Your Next.js App
To add a user profile to your Next.js app using Clerk, you need to obtain the frontend API key, create a new .env.local
file, and paste the frontend API key to a variable called NEXT_PUBLIC_CLERK_FRONTEND_API
. The .env.local
file should look similar to this:
Then you need to wrap your Next.js application with the ClerkProvider
component. The ClerkProvider
wrapper can be found in the @clerk/nextjs
SDK. The SDK also has methods called SignedIn
, SignedOut
, and RedirectToSignIn
. These components can be used to secure your application. For example, the components wrapped inside the SignedIn
will require the user to sign in. You can read about the different components in the official docs.
The _app.js
file for this application should look like this:
You must pass the API key in the ClerkProvider
through the frontendApi
prop. The publicPages
array can store the pages that are available to everyone. But for this article, all the pages will be secured.
The SignedIn
wrapper holds all the components. That means, if you are signed in, you'll only be able to access the pages. You'll be redirected to the sign-in page if you are not signed in. You'll be redirected to the login screen if you are not logged in using the RedirectToSignIn
component.
Header and User Profile
The Header
component is a very basic header. The code for the Header
component looks like this in the Header.jsx
file:
You can see that the Header
component is using a component called UserButton
. Clerk provides this component, and the button renders a toggle menu for accessing the user profile:
The userProfileUrl
prop holds the location of the Manage account page. Here, the location is /profile
.
Now, create a new page called profile.jsx
inside the pages
folder. You only need to render a single component to generate the user profile:
The UserProfile
component provided by Clerk does everything for you and generates an aesthetically pleasing user profile.
If you try to visit the /profile
route now, you'll need to sign in or create a new account. Clerk already handles the authorization for accessing specific pages. After successfully logging in, you'll be able to visit the user profile page:
You can also update your profile from here, which you'll learn about in the next section.
Implementing Custom User Profile
To implement a custom user profile, create a new page called view.jsx
inside your pages
directory. This page will render a custom user profile. As this article focuses more on the technicalities of implementing a custom user profile, the design and Tailwind classes will not be discussed.
To help the user access the custom user profile, update your index.jsx
file like this:
The previous code shows a centered text, "Clerk is Awesome," and a button for accessing the custom user profile with a link of /view
.
The final design of the custom profile page will look like this:
You'll have to use the useUser
hook available in the Clerk SDK to get the necessary information from the backend. The useUser
hook returns the values of the current user along with other important information, like the user creation date and external connected accounts if two-factor authentication is connected:
If you look at the returned data closely, you'll find that the data contains an object unsafeMetadata
. The unsafeMetadata
object can hold custom values stored for custom user profile information:
For this article, you can see there are two custom fields: customBio
and customName
.
Clerk has three types of metadata for storing additional user information: public, private, and unsafe. Both public and private metadata can be updated or added from the backend, and you can access or view only the public metadata from the frontend. The unsafe metadata can be read or written from the frontend:
Because of the ability to write from the frontend, this article will use unsafe metadata for custom user information. You can read more about metadata in Clerk's documentation.
Look at the view.jsx
file:
Don't get overwhelmed. The code can look complicated, but it's not. Now, break down the essential components. Begin by importing the useUser
hook from the Clerk SDK. Then the Image
and Link
components are imported from Next.js.
The ViewProfile
component renders the user profile. The initial step of using useUser
is to destructure its essential functions:
In the previous code, the functions check if the page is not loaded or the user is not signed in. If not, then nothing is rendered. You can console the user
object here:
This will return all the information available to Clerk for the particular user. Now that you have access to the user
object, you can use it to render the profile values. For example, you can generate the user's profile image by simply accessing the user.profileImageUrl
key. The first name of the user is stored inside the user.firstName
key.
The template here only uses these keys: user.profileImageUrl
, user.firstName
, user.lastName
, user.fullName
, user.emailAddresses
, and user.unsafeMetadata
. The custom user profile can be implemented using the user
object.
Updating Current User Profile
If you look at the previous code, you'll find that it also contains a link to another page for updating the profile information. Look at how you can edit user information from a custom profile update page.
Create a new page with the name additional.jsx
file inside the pages
directory. The react-hook-form
plug-in will be used here, though it's not necessary for a simple form like this. If your form is large and complex, react-hook-form
is a great solution. This plug-in makes the binding of the input fields simple. You can look at React Hook Form's "Get Started" example to get a basic idea of how it works.
Now take a look at the complete code and then break it into parts:
The onSubmit
function is used for saving the updated information to the server. The user.update
function is used for updating the values. A new object with the updated values is passed into this function:
As you can see from the previous object, the firstName
, lastName
, and two custom fields are being updated. The custom fields can be updated by updating the keys inside unsafeMetadata
.
The user.update
function is wrapped inside a try…catch
block. The page will be redirected to the custom user profile if the object is successfully updated.
But how do you render the already existing values of the user? It's implemented using a similar approach to building a custom user profile. The defaultValue
of the input field is filled with the corresponding user
object value:
The register
method is a react-hook-form
method that registers the input field with the value passed. For example, the previous code registers the value with firstName
. You can access this value by accessing the data.firstName
object.
Finally, the complete template is placed inside form
tags, where the onSubmit
function looks like this: onSubmit={handleSubmit(onSubmit)}
. The handleSubmit
function is a react-hook-form
function that handles submissions. It takes in another function as a parameter, and the onSubmit
function is passed here.
The last thing you need to do is add www.gravatar.com
to your next.config.js
file. When there is no profile picture set by the user for their profile, a Gravatar is shown. The image component in Next.js requires the hostnames to be added to the next.config.js
. Your next.config.js
file should look like this:
Your user profile update page is now ready.
You can access and check the page by visiting the localhost URL, http://localhost:3000/additional
. You can also check this GitHub repo for all the code from this tutorial.
The functionalities discussed earlier can also be implemented using the Clerk frontend API. The frontend API has endpoints like https://clerk.example.com/v1/me
for updating the user profile from the frontend. You can check the frontend API documentation to learn more.
Conclusion
Clerk is a great solution for quickly integrating authentication and custom user profiles into your application. It provides more than authentication; you can manage users, sessions, APIs, and more right from the Clerk dashboard.
This article aims to show you how custom user profiles can be built using the Next.js Clerk SDK. You also saw how Clerk components could be used for rapid development.
You can get started with Clerk for free for up to 500 monthly active users in your application. To create a Clerk account, visit their sign-up page.
Ready to get started?
Sign up today