Register Customer in the Storefront

Register a customer with email and password.

On this page

In this guide, you'll learn how to register a customer in your storefront.

On Next.js App Router, after sdk.store.auth.register succeeds: setAuthToken(token), revalidate customers, then transferCart(storeCode) so the guest cart belongs to the new customer. Do not keep the JWT in localStorage. See Login and Build a Next.js Storefront.

Aiminaabee register: sdk.store.auth.register(storeCode, "emailpass", { email, password, first_name, last_name }) creates the customer identity and record, then returns a JWT. You can store that token and optionally call sdk.store.customer.create if your flow still needs a separate customer payload.

Alternative Guides: - This guide covers registration using email and password. For authentication with third-party providers, refer to the Third-Party Login guide.

  • If you have email verification enabled, refer to the Verify Account guide instead.

Register Customer Flow

To register a customer, you implement the following steps:

A diagram illustrating the flow of the register customer flow

  1. Show the customer a form to enter their details.
  2. Send a POST request to the /auth/customer/emailpass/register Get Registration Token API route to obtain a registration JWT token.
  3. Send a request to the Register Customer API route passing the registration JWT token in the header.

However, a customer may enter an email that's already used either by an admin user, another customer, or a custom actor type. To handle this scenario:

  • Try to obtain a login token by sending a POST request to the /auth/customer/emailpass Authenticate Customer API route. The customer is only allowed to register if their email and password match the existing identity. This allows admin users to log in or register as customers.
  • If you obtained the login token successfully, register the customer using the login JWT token instead of the registration token. This will not remove the existing identity. So, for example, an admin user can also become a customer.

When you're using the JS SDK, this flow is simplified with quick registration and login methods. The rest of this guide uses the JS SDK to demonstrate the registration flow. However, if you're not using the JS SDK, you can still implement the same flow using the API routes.

Tip: Learn how to install and configure the JS SDK in the Getting started guide.


How to Implement the Register Customer Flow

An example implementation of the registration flow in a storefront:

React

tsx

tsxCopy
"use client" // include with Next.js 13+
import { useState } from "react"
import { sdk } from "@/lib/sdk"
import { FetchError } from "@aiminaabeejs/js-sdk"
export default function Register() {
const [loading, setLoading] = useState(false)
const [firstName, setFirstName] = useState("")
const [lastName, setLastName] = useState("")
const [email, setEmail] = useState("")
const [password, setPassword] = useState("")
const handleRegistration = async (
e: React.MouseEvent<HTMLButtonElement, MouseEvent>
) => {
e.preventDefault()
if (!firstName || !lastName || !email || !password) {
return
}
setLoading(true)
try {
await sdk.store.auth.register("us", "emailpass", {
email,
password,
})
} catch (error) {
const fetchError = error as FetchError
if (fetchError.statusText !== "Unauthorized" || fetchError.message !== "Identity with email already exists") {
alert(`An error occurred while creating account: ${fetchError}`)
return
}
// another identity (for example, admin user)
// exists with the same email. So, use the auth
// flow to login and create a customer.
const loginResponse = (await sdk.store.auth.login("us", "emailpass", {
email,
password,
}).catch((e) => {
alert(`An error occurred while creating account: ${e}`)
}))
if (!loginResponse) {
return
}
if (typeof loginResponse !== "string") {
alert("Authentication requires more actions, which isn't supported by this flow.")
return
}
}
// create customer
try {
const { customer } = await sdk.store.customer.create("us", {
first_name: firstName,
last_name: lastName,
email,
})
setLoading(false)
console.log(customer)
// TODO redirect to login page
} catch (error) {
console.error(error)
alert("Error: " + error)
return
}
}
return (
<form>
<input
type="text"
name="first_name"
value={firstName}
placeholder="First Name"
onChange={(e) => setFirstName(e.target.value)}
/>
<input
type="text"
name="last_name"
value={lastName}
placeholder="Last Name"
onChange={(e) => setLastName(e.target.value)}
/>
<input
type="email"
name="email"
value={email}
placeholder="Email"
onChange={(e) => setEmail(e.target.value)}
/>
<input
type="password"
name="password"
value={password}
placeholder="Password"
onChange={(e) => setPassword(e.target.value)}
/>
<button
disabled={loading}
onClick={handleRegistration}
>
Register
</button>
</form>
)
}

JS SDK

ts

tsCopy
// other imports...
import { FetchError } from "@aiminaabeejs/js-sdk"
const handleRegistration = async () => {
// obtain registration JWT token
try {
await sdk.store.auth.register("us", "emailpass", {
email,
password,
})
} catch (error) {
const fetchError = error as FetchError
if (fetchError.statusText !== "Unauthorized" || fetchError.message !== "Identity with email already exists") {
alert(`An error occurred while creating account: ${fetchError}`)
return
}
// another identity (for example, admin user)
// exists with the same email. So, use the auth
// flow to login and register a customer.
const loginResponse = (await sdk.store.auth.login("us", "emailpass", {
email,
password,
}).catch((e) => {
alert(`An error occurred while creating account: ${e}`)
}))
if (!loginResponse) {
return
}
if (typeof loginResponse !== "string") {
alert("Authentication requires more actions, which isn't supported by this flow.")
return
}
}
// register customer
try {
const { customer } = await sdk.store.customer.create("us", {
first_name: firstName,
last_name: lastName,
email,
})
console.log(customer)
// TODO redirect to login page
} catch (error) {
console.error(error)
alert("Error: " + error)
return
}
}

In the above example, you create a handleRegistration function that:

  • Obtains a registration JWT token from the /auth/customer/emailpass/register API route using the auth.register method. If an error is thrown:
    • If the error is an existing identity error, try retrieving the login JWT token from /auth/customer/emailpass API route using the auth.login method. This will fail if the existing identity has a different password, which doesn't allow the customer from registering.
    • For other errors, show an alert and exit execution.
    • The JS SDK automatically stores an re-uses the authentication headers or session in the auth.register and auth.login methods. So, if you're not using the JS SDK, make sure to pass the received authentication tokens as explained in the API reference
  • Send a request to the Register Customer API route to register the customer in Aiminaabee.
    • If an error occurs, show an alert and exit execution.
    • As mentioned, the JS SDK automatically sends the authentication headers or session in all requests after registration or logging in. If you're not using the JS SDK, make sure to pass the received authentication tokens as explained in the API reference.
  • Once the customer is registered successfully, you can either redirect the customer to the login page or log them in automatically, as explained in the Login guide.