From b025f107d46330d33d4cc17c764afebbd1cceb31 Mon Sep 17 00:00:00 2001 From: Eric Bailey Date: Wed, 16 Jul 2025 18:23:01 -0500 Subject: [PATCH] Handle did error --- .../ageAssurance/AgeAssuranceInitDialog.tsx | 46 +++++++++++++------ src/lib/hooks/useCreateSupportLink.ts | 39 ++++++++++++++++ 2 files changed, 70 insertions(+), 15 deletions(-) create mode 100644 src/lib/hooks/useCreateSupportLink.ts diff --git a/src/components/ageAssurance/AgeAssuranceInitDialog.tsx b/src/components/ageAssurance/AgeAssuranceInitDialog.tsx index ad13cc1c23..e3df8dabce 100644 --- a/src/components/ageAssurance/AgeAssuranceInitDialog.tsx +++ b/src/components/ageAssurance/AgeAssuranceInitDialog.tsx @@ -1,10 +1,15 @@ import {useState} from 'react' import {View} from 'react-native' +import {XRPCError} from '@atproto/xrpc' import {msg, Trans} from '@lingui/macro' import {useLingui} from '@lingui/react' import {validate as validateEmail} from 'email-validator' import {useCleanError} from '#/lib/hooks/useCleanError' +import { + SupportCode, + useCreateSupportLink, +} from '#/lib/hooks/useCreateSupportLink' import {useGetTimeAgo} from '#/lib/hooks/useTimeAgo' import {useTLDs} from '#/lib/hooks/useTLDs' import {isEmailMaybeInvalid} from '#/lib/strings/email' @@ -66,6 +71,7 @@ function Inner() { const {lastInitiatedAt} = useAgeAssuranceContext() const getTimeAgo = useGetTimeAgo() const tlds = useTLDs() + const createSupportLink = useCreateSupportLink() const wasRecentlyInitiated = lastInitiatedAt && @@ -79,7 +85,7 @@ function Inner() { const [language, setLanguage] = useState( convertToKWSSupportedLanguage(langPrefs.appLanguage), ) - const [error, setError] = useState('') + const [error, setError] = useState(null) const {mutateAsync: init, isPending} = useInitAgeAssurance() @@ -125,22 +131,32 @@ function Inner() { setSuccess(true) } catch (e) { - const {clean, raw} = cleanError(e) - - if (clean) { - setError(clean || _(msg`Something went wrong, please try again`)) - } else { - let message = _(msg`Something went wrong, please try again`) - - if (raw) { - if (raw.startsWith('This email address is not supported')) { - message = _( + if (e instanceof XRPCError) { + if (e.error === 'InvalidEmail') { + setError( + _( msg`Please enter a valid, non-temporary email address. You may need to access this email in the future.`, - ) - } + ), + ) + } else if (e.error === 'DidTooLong') { + setError( + <> + + We're having issues initializing the age assurance process for + your account. Please{' '} + + contact support + {' '} + for assistance. + + , + ) } - - setError(message) + } else { + const {clean, raw} = cleanError(e) + setError(clean || raw || _(msg`Something went wrong, please try again`)) } } } diff --git a/src/lib/hooks/useCreateSupportLink.ts b/src/lib/hooks/useCreateSupportLink.ts new file mode 100644 index 0000000000..5ec7578c5a --- /dev/null +++ b/src/lib/hooks/useCreateSupportLink.ts @@ -0,0 +1,39 @@ +import {useCallback} from 'react' +import {msg} from '@lingui/macro' +import {useLingui} from '@lingui/react' + +import {useSession} from '#/state/session' + +export const ZENDESK_SUPPORT_URL = + 'https://blueskyweb.zendesk.com/hc/requests/new' + +export enum SupportCode { + AA_DID = 'AA_DID', +} + +/** + * {@link https://support.zendesk.com/hc/en-us/articles/4408839114522-Creating-pre-filled-ticket-forms} + */ +export function useCreateSupportLink() { + const {_} = useLingui() + const {currentAccount} = useSession() + + return useCallback( + ({code, email}: {code: SupportCode; email?: string}) => { + const url = new URL(ZENDESK_SUPPORT_URL) + if (currentAccount) { + url.search = new URLSearchParams({ + tf_anonymous_requester_email: email || currentAccount.email || '', // email will be defined + tf_description: + `[Code: ${code}] — ` + _(msg`Please write your message below:`), + /** + * Custom field specific to {@link ZENDESK_SUPPORT_URL} form + */ + tf_17205412673421: currentAccount.handle + ` (${currentAccount.did})`, + }).toString() + } + return url.toString() + }, + [_, currentAccount], + ) +}