Skip to content

Commit

Permalink
fix(elements): only validate onFocus or onBlur when value has cha…
Browse files Browse the repository at this point in the history
…nged (#3778)
  • Loading branch information
alexcarpenter authored Jul 22, 2024
1 parent ae41f6a commit 6a46425
Show file tree
Hide file tree
Showing 2 changed files with 20 additions and 4 deletions.
5 changes: 5 additions & 0 deletions .changeset/strong-beers-compete.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@clerk/elements": patch
---

Fix issue where password field validation was incorrectly showing successful field state due to input being refocused on invalid form submission
19 changes: 15 additions & 4 deletions packages/elements/src/react/common/form/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,16 @@ const enrichFieldState = (validity: ValidityState | undefined, fieldState: Field
* Hooks
* -----------------------------------------------------------------------------------------------*/

function usePrevious<T>(value: T): T | undefined {
const ref = React.useRef<T>();

React.useEffect(() => {
ref.current = value;
}, [value]);

return ref.current;
}

const useGlobalErrors = () => {
const errors = useFormSelector(globalErrorsSelector);

Expand Down Expand Up @@ -251,6 +261,7 @@ const useInput = ({
},
});
const value = useFormSelector(fieldValueSelector(name));
const prevValue = usePrevious(value);
const hasValue = Boolean(value);
const type = inputType ?? determineInputTypeFromName(rawName);
let shouldValidatePassword = false;
Expand Down Expand Up @@ -288,21 +299,21 @@ const useInput = ({
const onBlur = React.useCallback(
(event: React.FocusEvent<HTMLInputElement>) => {
onBlurProp?.(event);
if (shouldValidatePassword) {
if (shouldValidatePassword && event.target.value !== prevValue) {
validatePassword(event.target.value);
}
},
[onBlurProp, shouldValidatePassword, validatePassword],
[onBlurProp, shouldValidatePassword, validatePassword, prevValue],
);

const onFocus = React.useCallback(
(event: React.FocusEvent<HTMLInputElement>) => {
onFocusProp?.(event);
if (shouldValidatePassword) {
if (shouldValidatePassword && event.target.value !== prevValue) {
validatePassword(event.target.value);
}
},
[onFocusProp, shouldValidatePassword, validatePassword],
[onFocusProp, shouldValidatePassword, validatePassword, prevValue],
);

React.useEffect(() => {
Expand Down

0 comments on commit 6a46425

Please sign in to comment.