Build Identifier First Signup with Password

Before you start

You will need:

  • A non-production Auth0 tenant with a custom domain-configured application.

  • A sample app running on your localhost with Universal Login configured. For example: A React sample app.

  • A single-page application to implement Auth0 ACUL JS SDK. You can clone our boilerplate app to implement the customized login interface: git clone https://github.com/auth0/auth0-acul-react-boilerplate

By the end of this guide, you'll have an identity-first flow with customized Signup ID and Signup Password screens. To learn more, read the Getting Started guide and visit the SDK reference guide.

Setup

In your Auth0 Dashboard, set up Universal Login, Identifier First Authentication, and a Database Connection that uses passwords.

Run a single-page application to build custom login screens. To understand the context for Advanced Customizations interfaces, clone our boilerplate app: git clone https://github.com/auth0/auth0-acul-react-boilerplate

Install the ACUL SDK. After cloning the react boilerplate, change the directory to the auth0-acul-react-boilerplate folder and install the SDK.

// open the directory where you git clone the boilerplate
cd auth0-acul-react-boilerplate && npm i
// Install the ACUL JS SDK
npm install @auth0/auth0-acul-js

Was this helpful?

/

1. Build the signup-id screen

Signup ID

Below is a full sample of the Screen.

/

import { ChangeEvent } from "react";
import { SignupId as ScreenProvider } from "@auth0/auth0-acul-js";

// UI Components
import { Label } from "@/components/ui/label";
import { Input } from "@/components/ui/input";
import { Button } from "@/components/ui/button";
import { Text } from "@/components/ui/text";
import { Link } from "@/components/ui/link";
import {
  CardHeader,
  CardTitle,
  CardDescription,
  CardContent,
} from "@/components/ui/card";

export default function SignupId() {
  // Initialize the SDK for this screen
  const screenProvider = new ScreenProvider();

  // Handle the submit action
  const formSubmitHandler = (event: ChangeEvent<HTMLFormElement>) => {
    event.preventDefault();

    // grab the value from the form
    const identifierInput = event.target.querySelector(
      "input#identifier"
    ) as HTMLInputElement;

    // Call the SDK
    screenProvider.signup({ email: identifierInput?.value });
  };

  // Render the form
  return (
    <form noValidate onSubmit={formSubmitHandler}>
      <CardHeader>
        <CardTitle className="mb-2 text-3xl font-medium text-center">
          {screenProvider.screen.texts?.title ?? "Welcome"}
        </CardTitle>
        <CardDescription className="mb-8 text-center">
          {screenProvider.screen.texts?.description ?? "Create your account"}
        </CardDescription>
      </CardHeader>
      <CardContent>
        <div className="mb-2 space-y-2">
          <Label htmlFor="identifier">
            {screenProvider.screen.texts?.emailPlaceholder ??
              "Enter your email"}
          </Label>
          <Input
            type="text"
            id="identifier"
            name="identifier"
            defaultValue={
              screenProvider.screen.data?.email ??
              screenProvider.untrustedData.submittedFormData?.email
            }
          />
        </div>
        <Button type="submit" className="w-full">
          {screenProvider.screen.texts?.buttonText ?? "Continue"}
        </Button>
        <Text>
          {screenProvider.screen.texts?.footerText ??
            "Already have an account?"}
          <Link className="ml-1" href={screenProvider.screen.loginLink ?? "#"}>
            {screenProvider.screen.texts?.footerLinkText ??
              "Log into your account"}
          </Link>
        </Text>
      </CardContent>
    </form>
  );
}

Was this helpful?

/

Import and initialize the SDK

In the auth0-acul-react-boilerplate/src folder, create a folder called screens and a file called Login.tsx. Import the SDK and in the React component initialize the SDK for the screen.

import { SignupId as ScreenProvider } from "@auth0/auth0-acul-js";

export default function SignupId() {
  // Initialize the SDK for this screen
  const screenProvider = new ScreenProvider();
  ...
}

Was this helpful?

/

Use the SDK to access properties and methods on the screen

Using the SDK you can access the properties and methods of the screen. The Auth0 ACUL JS SDK provides properties and methods to access the data.

For more information about context data, read Universal Login Context Data.

Implement the signup action

Locate the button click function in the Login.tsx file to implement the signup action.

<form noValidate onSubmit={formSubmitHandler}>
    ...
      <CardContent>
        <div className="mb-2 space-y-2">
          <Label htmlFor="identifier">
            {screenProvider.screen.texts?.emailPlaceholder ??
              "Enter your email"}
          </Label>
          <Input
            type="text"
            id="identifier"
            name="identifier"
            defaultValue={
              screenProvider.screen.data?.email ??
              screenProvider.untrustedData.submittedFormData?.email
            }
          />
        </div>
        <Button type="submit" className="w-full">
          {screenProvider.screen.texts?.buttonText ?? "Continue"}
        </Button>
      </CardContent>
    </form>
  );
}

Was this helpful?

/

Call the submit action

Using the SDK, submit the data captured in the screen to the server. The server process this data and will route the user to the next step in the flow. If there are errors, this screen is reloaded, allowing you to display them to the user. Errors are accessed from the SDK.

const formSubmitHandler = (event: ChangeEvent<HTMLFormElement>) => {
    event.preventDefault();

    // grab the value from the form
const identifierInput = event.target.querySelector(
      "input#identifier"
    ) as HTMLInputElement;

    // Call the SDK
    screenProvider.signup({ email: identifierInput?.value });
  };

Was this helpful?

/

2: Build the signup-password screen

Signup Password with Flexible IDs

Below is a full sample of the Screen.

/

import { ChangeEvent } from "react";
import { SignupPassword as ScreenProvider } from "@auth0/auth0-acul-js";

// UI Components
import { Label } from "@/components/ui/label";
import { Input } from "@/components/ui/input";
import { Button } from "@/components/ui/button";
import { Text } from "@/components/ui/text";
import { Link } from "@/components/ui/link";
import {
  CardHeader,
  CardTitle,
  CardDescription,
  CardContent,
} from "@/components/ui/card";

export default function SignupPassword() {
  // Initialize the SDK for this screen
  const screenProvider = new ScreenProvider();

  // Handle the submit action
  const formSubmitHandler = (event: ChangeEvent<HTMLFormElement>) => {
    event.preventDefault();

  // grab the value from the form
    const identifierInput = event.target.querySelector(
      "input#identifier"
    ) as HTMLInputElement;
    const passwordInput = event.target.querySelector(
      "input#password"
    ) as HTMLInputElement;

    // Call the SDK
    screenProvider.signup({
      email: identifierInput?.value,
      password: passwordInput?.value,
    });
  };

  // Render the form
  return (
    <form noValidate onSubmit={formSubmitHandler}>
      <CardHeader>
        <CardTitle className="mb-2 text-3xl font-medium text-center">
          {screenProvider.screen.texts?.title ?? "Enter Your Password"}
        </CardTitle>
        <CardDescription className="mb-8 text-center">
          {screenProvider.screen.texts?.description ??
            "Enter your password to continue"}
        </CardDescription>
      </CardHeader>
      <CardContent>
        <Text className="mb-4 text-large">
          <span className="inline-block">
            Sign up as
            <span className="inline-block ml-1 font-bold">
              {screenProvider.screen.data?.email}.
            </span>
          </span>
          <Link
            href={screenProvider.screen.editLink ?? "#"}
            className="ml-2"
          >
            {screenProvider.screen.texts?.editEmailText ?? "Edit Email"}
          </Link>
        </Text>
        <Input
          type="hidden"
          name="identifier"
          id="identifier"
          value={screenProvider.screen.data?.email}
        />
        <div className="mb-2 space-y-2">
          <Label htmlFor="password">
            {screenProvider.screen.texts?.passwordPlaceholder ?? "Password"}
          </Label>
          <Input type="password" id="password" name="password" />
        </div>
        <Button type="submit" className="w-full">
          {screenProvider.screen.texts?.buttonText ?? "Continue"}
        </Button>
        <Text>
          {screenProvider.screen.texts?.footerText ??
            "Already have an account?"}
          <Link className="ml-1" href={screenProvider.screen.loginLink ?? "#"}>
            {screenProvider.screen.texts?.footerLinkText ??
              "Log into your account"}
          </Link>
        </Text>
      </CardContent>
    </form>
  );
}

Was this helpful?

/

Import and initialize the SDK

In the auth0-acul-react-boilerplate/src folder, create a folder called screens and a file called Login.tsx. Import the SDK , then use the the React component to initialize the SDK for the screen.

import { SignupPassword as ScreenProvider } from "@auth0/auth0-acul-js";

export default function SignupPassword() {
  // Initialize the SDK for this screen
const screenProvider = new ScreenProvider();
  ...
  }

Was this helpful?

/

Use the SDK to access properties and methods on the screen

Using the SDK you can access the properties and methods of the screen. The Auth0 ACUL JS SDK provides properties and methods to access the data.

For more information about context data, read Universal Login Context Data.

<form noValidate onSubmit={formSubmitHandler}>
      ...
  <CardContent>
   <Text className="mb-4 text-large">
    <span className="inline-block">
      Sign up as
   <span className="inline-block ml-1 font-bold">
   {screenProvider.screen.data?.email}.
  </span>
 </span>
  <Link
   href={screenProvider.screen.editLink ?? "#"}
    className="ml-2"
   >
   {screenProvider.screen.texts?.editEmailText ?? "Edit Email"}
  </Link>
  </Text>
  <Input
  type="hidden"
  name="identifier"
         id="identifier"
         value={screenProvider.screen.data?.email}
        />
 <div className="mb-2 space-y-2">
   <Label htmlFor="password">
     {screenProvider.screen.texts?.passwordPlaceholder ?? "Password"}
    </Label>
    <Input type="password" id="password" name="password" />
   </div>
  <Button type="submit" className="w-full">
     {screenProvider.screen.texts?.buttonText ?? "Continue"}
    </Button>
  ...
      </CardContent>
    </form>

Was this helpful?

/

Call the submit action

Using the SDK, submit the data captured in the screen to the server. The server process this data and will route the user to the next step in the flow. If there are errors, this screen is reloaded, allowing you to display them to the user. Errors are accessed from the SDK.

const formSubmitHandler = (event: ChangeEvent<HTMLFormElement>) => {
    event.preventDefault();

  // grab the value from the form
    const identifierInput = event.target.querySelector(
      "input#identifier"
    ) as HTMLInputElement;
    const passwordInput = event.target.querySelector(
      "input#password"
    ) as HTMLInputElement;

    // Call the SDK
    screenProvider.signup({
      email: identifierInput?.value,
      password: passwordInput?.value,
    });
  };

Was this helpful?

/

3: Configure ACUL to use local assets

Use Auth0 CLI, Terraform, or the Management API to enable ACUL. For details about what can be configured, read Configure ACUL Screens.

In the root directory of your project, create a settings folder and include in it a {SCREENNAME}.json file.

//settings.json
{
  "rendering_mode": "advanced",
  "context_configuration": [
    "screen.texts"
  ],
  "default_head_tags_disabled": false,
  "head_tags": [
    {
      "attributes": {
        "async": true,
        "defer": true,
        "integrity": [
          "ASSET_SHA"
        ],
        "src": "http://127.0.0.1:8080/index.js"
      },
      "tag": "script"
    },
    {
      "attributes": {
        "href": "http://127.0.0.1:8080/index.css",
        "rel": "stylesheet"
      },
      "tag": "link"
    }
  ]
}

Was this helpful?

/
 Enable ACUL with Auth0 CLI:

auth0 ul customize --rendering-mode advanced --prompt {SCREENNAME} --screen {SCREENNAME} --settings-file ./settings/{SCREENNAME}.json

Was this helpful?

/

Test your configuration on a local server

ACUL requires assets to be hosted on a public URL. Run a local server and test your assets before deploying them.

npm run build

cd dist
npx serve -p 8080 // serve the assets on your local machine

Was this helpful?

/

4: Deploy the assets and update your tenant configuration

Advanced Customization for Universal Login works with all modern Javascript bundlers. like Vite and Webpack. For more information, read Deploy Advanced Customizations to Production.

For more information about deploying ACUL to your tenant, read Configure ACUL Screens.

Read... To learn...                                
Advanced Customizations for Universal Login How Advanced Customizations work.
Getting Started with Advanced Customizations Getting Started basics for Advanced Customizations
Advanced Customizations for Universal Login: Screens A list of all screens available for Advanced Customizations.