Implementing WebAuthn in Next.js: A Hands-On Guide
A hands-on guide to implementing WebAuthn in Next.js with live code examples.
Welcome back to our WebAuthn series. In our previous articles, we've covered the basics of WebAuthn, and a 101 guide. If you're just joining us, feel free to check out these foundational pieces to get up to speed.
Today, we're rolling up our sleeves to put theory into practice. We'll be harnessing the power of Next.js with the new feature “Server Actions”. Our goal? To implement WebAuthn in a Next.js application, and get ourselves ready for WebAuthn.
Before we dive into the coding sea, here's a glimpse of what awaits you at the journey's end - a fully functional demo website. Explore it to see WebAuthn in action and to get a taste of what you'll be building. In this demo website, you can register new users and login with the passkeys just registered.
And for those who prefer a map in hand, we've got you covered! All the code we'll be discussing is available in a public GitHub repository . This repository is your companion guide, offering the full source code of our implementation.
Ready to embark on this exciting adventure? Let's get started!
Prerequisites
Before we begin, let's make sure we have everything we need:
- A Next.js Project: If you haven't set up a Next.js project yet, here's a quick guide to get you started.
- Simple WebAuthn Library: Several packages to help reduce the amount of work needed to incorporate WebAuthn into a website. Use your favorite package manager to install
@simplewebauthn/browser
,@simplewebauthn/server
and@simplewebauthn/typescript-types
- Session Storage: We'll be using session storage to manage WebAuthn challenges. We’ll use vercel’s KV to achieve this.
- A User Database: A place to store our users' registered passkeys. To keep it simple, we’ll also use vercel’s KV to demonstrate.
Now, with our tools and materials at hand, we're ready to start building.
Implementing session storage with Vercel’s KV
Setting up KV storage
It is easy to initialize a KV storage both in production and local development, follow this guide to connect a KV store to your project and pull the environment values: https://vercel.com/docs/storage/vercel-kv/quickstart
Implement session management functions
We exported 2 functions:
getCurrentSession
: Use Next.js cookie helper to create a session for current request, and return the value.updateCurrentSession
: Save data to current session.
Implementing user database with Vercel’s KV
Similarly to our session implementation, let's implement a simple user database.
We created functions to find user by email, and update user data by email. Remember, this is for demonstration only, in the real product, the user data is kept in database usually.
Preparing WebAuthn functions
Before we proceed, let’s see the diagram of registration and authentication flow:
As you can see, we need to prepare 2 functions:
generateWebAuthnRegistrationOptions
verifyWebAuthnRegistration
Similar to registration, the login requires 2 functions:
generateWebAuthnLoginOptions
verifyWebAuthnLogin
Here’s the code:
Build the web page
We’ve completed the preparation, let’s build the page:
Conclusion
Congratulations on navigating through the intricacies of implementing WebAuthn in a Next.js application. As we wrap up, it's important to address some crucial considerations for deploying it in a production environment.
Key Considerations for Production Deployment
- User Identifier Adjustment: In this tutorial, we used an email address as the user identifier. However, in a production scenario, you might need to use a different identifier, such as a
userId
orusername
. - Database Integration: While we utilized Vercel’s KV as a simple demonstration of session and user data management, a real-world application should integrate a more robust database system (like PostgreSQL, MongoDB, etc.)
- Customizing WebAuthn Options: The WebAuthn options we explored are a starting point. Depending on your application's requirements and security policies, you may need to adjust these settings. Consult the WebAuthn documentation and the Simple WebAuthn library's documentation for guidance on customizing these options to suit your specific needs.
Thank you for joining us on this educational adventure. Even in this minimal example, integrating WebAuthn is not a simple task, there is another option, try WebAuthn in Logto’s MFA: