mirror of
https://github.com/Tria-plc/edr-platform.git
synced 2026-09-08 04:15:43 +00:00
fix: onboarding validation
This commit is contained in:
@@ -26,9 +26,22 @@ interface ETradeInfoProps {
|
||||
onStatusChange?: (status: ETradeStatus) => void;
|
||||
/** Called when the TIN changes away from the last fetched value — clear whatever it filled in. */
|
||||
onReset?: () => void;
|
||||
/**
|
||||
* This TIN already passed eTrade in an earlier session (the saved profile
|
||||
* carries its registration details), so adopt it on arrival instead of
|
||||
* re-querying. Rehydration lands the TIN after the first render, which used
|
||||
* to look exactly like the customer typing a new one: every reopen fired a
|
||||
* live lookup that could fail on an outage, and re-marked eTrade's fields as
|
||||
* freshly verified so they were resubmitted on the next save. "Get Data"
|
||||
* stays available for a deliberate re-verify.
|
||||
*/
|
||||
alreadyVerified?: boolean;
|
||||
}
|
||||
|
||||
const isValidTin = (tin: string) => tin.length === 10;
|
||||
// Digits, not just length: a 10-character non-numeric TIN used to fire a lookup
|
||||
// that could only fail, and the failure was then reported as "this TIN isn't
|
||||
// registered with eTrade" instead of "that isn't a TIN".
|
||||
const isValidTin = (tin: string) => /^\d{10}$/.test(tin);
|
||||
|
||||
export default function ETradeInfo({
|
||||
tin,
|
||||
@@ -37,6 +50,7 @@ export default function ETradeInfo({
|
||||
onDataLoaded,
|
||||
onStatusChange,
|
||||
onReset,
|
||||
alreadyVerified,
|
||||
}: ETradeInfoProps) {
|
||||
const mutation = useETradeData();
|
||||
const isLoading = mutation.isPending;
|
||||
@@ -63,6 +77,13 @@ export default function ETradeInfo({
|
||||
// doesn't refire the lookup the moment this mounts.
|
||||
const lastFetchedTin = useRef<string | null>(tin || null);
|
||||
useEffect(() => {
|
||||
// A rehydrated TIN that eTrade already accepted: adopt it silently. Doing
|
||||
// this before the change-detection below also keeps `onReset` from firing,
|
||||
// which would wipe the very registration details that prove it passed.
|
||||
if (alreadyVerified && lastFetchedTin.current === null && isValidTin(tin)) {
|
||||
lastFetchedTin.current = tin;
|
||||
return;
|
||||
}
|
||||
if (tin !== lastFetchedTin.current) {
|
||||
// TIN moved away from whatever we last fetched — that result (verified
|
||||
// data, "taken", or an error) no longer describes this TIN. Drop it so
|
||||
@@ -82,12 +103,17 @@ export default function ETradeInfo({
|
||||
|
||||
const apiError =
|
||||
mutation.isError && mutation.error ? extractApiError(mutation.error) : null;
|
||||
// A 400 here means eTrade simply has no record for this TIN.
|
||||
const notFound = apiError?.statusCode === 400;
|
||||
// A 400 here usually means eTrade has no record for this TIN — but the API
|
||||
// also wraps its own transport failures as a 400 ("Failed to fetch company
|
||||
// info from eTrade: …"), and reporting an outage as "this TIN isn't
|
||||
// registered" sends the customer off to re-check a number that was fine.
|
||||
const unreachable = /failed to fetch/i.test(apiError?.message ?? "");
|
||||
const notFound = apiError?.statusCode === 400 && !unreachable;
|
||||
const errorMessage =
|
||||
apiError && !notFound
|
||||
? apiError.message ||
|
||||
"We couldn't reach eTrade to fetch your company information. Please try again."
|
||||
? unreachable || !apiError.message
|
||||
? "We couldn't reach eTrade to fetch your company information. Please try again in a moment."
|
||||
: apiError.message
|
||||
: null;
|
||||
|
||||
const status: ETradeStatus = isLoading
|
||||
|
||||
Reference in New Issue
Block a user