import { getOrgUsernameFromEmail } from "@calcom/features/auth/signup/utils/getOrgUsernameFromEmail"; import prisma from "@calcom/prisma"; export const getUsernameForOrgMember = async ({ email, orgAutoAcceptEmail, isSignup, username, }: { username?: string; email: string; orgAutoAcceptEmail?: string; isSignup: boolean; }) => { if (isSignup) { // We ensure that the username is always derived from the email during signup. return getOrgUsernameFromEmail(email, orgAutoAcceptEmail || ""); } if (!username) { throw new Error("Username is required"); } // Right now it's not possible to change username in an org by the user but when that's allowed we would simply accept the provided username return username; }; export const validateAndGetCorrectedUsernameAndEmail = async ({ username, email, organizationId, orgAutoAcceptEmail, isSignup, }: { username: string; email: string; organizationId?: number; orgAutoAcceptEmail?: string; isSignup: boolean; }) => { if (username.includes("+")) { return { isValid: false, username: undefined, email }; } // There is an existingUser if, within an org context or not, the username matches // OR if the email matches AND either the email is verified // or both username and password are set const existingUser = await prisma.user.findFirst({ where: { ...(organizationId ? { organizationId } : {}), OR: [ // When inviting to org, invited user gets created with username now, so in an org context we // can't check for username as it will exist on signup ...(!organizationId ? [{ username }] : [{}]), { AND: [ { email }, { OR: [ { emailVerified: { not: null } }, { AND: [{ password: { isNot: null } }, { username: { not: null } }] }, ], }, ], }, ], }, select: { email: true, }, }); let validatedUsername = username; if (organizationId) { validatedUsername = await getUsernameForOrgMember({ email, orgAutoAcceptEmail, isSignup, }); } return { isValid: !existingUser, username: validatedUsername, email: existingUser?.email }; }; export const validateAndGetCorrectedUsernameInTeam = async ( username: string, email: string, teamId: number, isSignup: boolean ) => { try { const team = await prisma.team.findFirst({ where: { id: teamId, }, select: { metadata: true, isOrganization: true, parentId: true, organizationSettings: true, parent: { select: { organizationSettings: true, }, }, }, }); console.log("validateAndGetCorrectedUsernameInTeam", { teamId, team, }); const organization = team?.isOrganization ? team : team?.parent; if (organization) { // Organization context -> org-context username check const orgId = team?.parentId || teamId; return validateAndGetCorrectedUsernameAndEmail({ username, email, organizationId: orgId, orgAutoAcceptEmail: organization?.organizationSettings?.orgAutoAcceptEmail || "", isSignup, }); } else { // Regular team context -> regular username check return validateAndGetCorrectedUsernameAndEmail({ username, email, isSignup }); } } catch (error) { console.error(error); return { isValid: false, username: undefined, email: undefined }; } };