User ID Mapping
tip
If you have not stored your user's Auth0 userId in your database you can ignore this section.
If you store your user's Auth0 userId
in your tables you will need to map the user's Auth0 userId
to their SuperTokens userId
and override SuperTokens functions so the correct userId
is used.
In this section we will go over:
- The functions used to set and retrive
userId
data used in the Modifications to login section, - How to override the necessary SuperTokens functions to use the correct
userId
.
#
UserId Mapping functionsWe will need the following two functions:
setUserIdMapping()
getUserIdMapping()
// The function is used in the Modifications to Login section to map a users newly created SuperTokens userIds with their Auth0 userIdlet setUserIdMapping = async ( input: { auth0UserId: string, supertokensUserId: string }): Promise<void> => { // set the mapping in your data store}
// The function retrieves the userId mapping using either the SuperTokens or Auth0 userId.let getUserIdMapping = async ( input: { auth0UserId?: string, supertokensUserId?: string }): Promise<{ auth0UserId: string, supertokensUserId: string } | undefined> => {
// get mapped userIds if the input userId exits in your data store // getUserIdMappingIfExists is a function defined by you let userIdMapping = getUserIdMappingIfExists(input)
// if input userId exists get the mapped user data if (userIdMapping !== undefined) {
return ({ auth0UserId: userIdMapping.auth0UserId, supertokensUserId: userIdMapping.supertokensUserId }) }
return undefined}
userId
as input or return userId
in their response:#
Overriding all functions on the backend which take If a user has an Auth0 userId
mapped to an SuperTokens userId
, then:
- A SuperTokens function which has
userId
in its input should replace the Auth0userId
in the input object with the SuperTokensuserId
- A SuperTokens function which returns
userId
in its response should replace the SuperTokensuserId
in the response object with the Auth0userId
The following functions need to be modified so that the correct userId
is used:
getUserByEmail
getUserById
getUserByPhoneNumber
updateUser
Nodejs
import Passwordless from "supertokens-node/recipe/passwordless";
let getUserIdMapping = async ( input: { auth0UserId?: string, supertokensUserId?: string }): Promise<{ auth0UserId: string, supertokensUserId: string } | undefined> => { // TODO: See previous step return undefined;}
Passwordless.init({ flowType: "USER_INPUT_CODE_AND_MAGIC_LINK", contactMethod: "EMAIL_OR_PHONE", createAndSendCustomEmail: async (input, context) => { // Handle sending email }, createAndSendCustomTextMessage: async (input, context) => { // Handle sending sms }, override: { functions: (originalImpl) => { return { ...originalImpl, getUserByEmail: async function (input) { let response = await originalImpl.getUserByEmail(input)
if (response === undefined) { return undefined }
// get userId mapping if it exists let userIdMappingInfo = await getUserIdMapping({ supertokensUserId: response.id })
// set Auth0 userId in the response if (userIdMappingInfo !== undefined) { response.id = userIdMappingInfo.auth0UserId }
return response }, getUserById: async function (input) {
// get userId mapping if it exists let userIdMappingInfo = await getUserIdMapping({ auth0UserId: input.userId })
if (userIdMappingInfo !== undefined) { // call original implementation with the mapped SuperTokens userId let response = await originalImpl.getUserById({ userId: userIdMappingInfo.supertokensUserId, userContext: undefined })
if (response === undefined) { return response }
// set Auth0 userId in the response response.id = userIdMappingInfo.auth0UserId return response }
return await originalImpl.getUserById(input) }, getUserByPhoneNumber: async function (input) { let response = await originalImpl.getUserByPhoneNumber(input)
if (response === undefined) { return response }
// get userId mapping if it exists let userIdMappingInfo = await getUserIdMapping({ supertokensUserId: response.id })
if (userIdMappingInfo !== undefined) { // set Auth0 userId in the response response.id = userIdMappingInfo.auth0UserId }
return response }, updateUser: async function (input) {
// get userId mapping if it exists let userIdMappingInfo = await getUserIdMapping({ auth0UserId: input.userId }) if (userIdMappingInfo !== undefined) { // set the mapped SuperTokens userId in the input input.userId = userIdMappingInfo.supertokensUserId }
return await originalImpl.updateUser(input); } } } },})