import { gql } from '@apollo/client'; import { Input } from 'antd'; import { useEffect, useState } from 'react'; import { Helmet } from 'react-helmet-async'; import { Link, useNavigate, useParams } from 'react-router-dom'; import FullScreenLoading from '../../components/common/FullScreenLoading'; import CoopButton from '../dashboard/components/CoopButton'; import { namedOperations, useGQLInviteUserTokenQuery, useGQLSignUpMutation, } from '../../graphql/generated'; import LogoBlack from '../../images/LogoBlack.png'; gql` query InviteUserToken($token: String!) { inviteUserToken(token: $token) { ... on InviteUserTokenSuccessResponse { tokenData { token email role orgId samlEnabled } } ... on InviteUserTokenExpiredError { title } ... on InviteUserTokenMissingError { title } } } mutation SignUp($input: SignUpInput!) { signUp(input: $input) { ... on SignUpSuccessResponse { data { id loginMethods } } ... on SignUpUserExistsError { title } } } `; /** * Sign Up form component - Token-only version */ export default function SignUp() { const [password, setPassword] = useState(undefined); const [firstName, setFirstName] = useState(undefined); const [lastName, setLastName] = useState(undefined); const [errorMessage, setErrorMessage] = useState( undefined, ); const navigate = useNavigate(); const { token } = useParams<{ token: string }>(); // Fetch token data const { data: tokenData, loading: tokenLoading, error: tokenError, } = useGQLInviteUserTokenQuery({ variables: { token: token ?? '' }, skip: !token, }); const [signUp, { loading: signUpLoading }] = useGQLSignUpMutation({ refetchQueries: [namedOperations.Query.LoggedInUserForRoute], onCompleted: (data) => { if (data.signUp.__typename === 'SignUpSuccessResponse') { navigate('/dashboard'); } else if (data.signUp.__typename === 'SignUpUserExistsError') { setErrorMessage( 'An account with this email already exists. Please log in instead.', ); } }, onError: (error) => { setErrorMessage(error.message ?? 'An error occurred during sign up.'); }, }); const tokenInfo = tokenData?.inviteUserToken?.__typename === 'InviteUserTokenSuccessResponse' ? tokenData.inviteUserToken.tokenData : null; const tokenErrorMessage = tokenData?.inviteUserToken?.__typename === 'InviteUserTokenExpiredError' || tokenData?.inviteUserToken?.__typename === 'InviteUserTokenMissingError' ? tokenData.inviteUserToken.title : null; useEffect(() => { if (!token) { setErrorMessage('No invitation token provided.'); } }, [token]); const onSignUp = async () => { if (!tokenInfo) { setErrorMessage('Invalid or expired invitation token.'); return; } if (!firstName || !lastName) { setErrorMessage('Please enter your first and last name.'); return; } if (tokenInfo.samlEnabled) { // SAML-enabled signup await signUp({ variables: { input: { email: tokenInfo.email, firstName, lastName, role: tokenInfo.role, orgId: tokenInfo.orgId, inviteUserToken: token!, loginMethod: 'SAML', }, }, }); } else { // Password-based signup if (!password || password.length < 8) { setErrorMessage('Password must be at least 8 characters long.'); return; } await signUp({ variables: { input: { email: tokenInfo.email, password, firstName, lastName, role: tokenInfo.role, orgId: tokenInfo.orgId, inviteUserToken: token!, loginMethod: 'PASSWORD', }, }, }); } }; if (tokenLoading) { return ; } if (tokenError || tokenErrorMessage || !token) { return (
Invalid Invitation | Coop
Coop Logo

Invalid or Expired Invitation

{tokenErrorMessage ?? 'This invitation link is invalid or has expired. Please contact your administrator for a new invitation.'}

); } if (!tokenInfo) { return ; } return (
Sign Up | Coop
Coop Logo

Complete Your Account

You've been invited to join as{' '} {tokenInfo.email}

{errorMessage && (
{errorMessage}
)}
setFirstName(e.target.value)} size="large" />
setLastName(e.target.value)} size="large" />
{!tokenInfo.samlEnabled && (
setPassword(e.target.value)} size="large" />
)}
Already have an account?{' '} Log in
); }