diff --git a/src/common-components/AuthnValidationFormGroup.jsx b/src/common-components/AuthnValidationFormGroup.jsx
index 34e46f1a..cc52478c 100644
--- a/src/common-components/AuthnValidationFormGroup.jsx
+++ b/src/common-components/AuthnValidationFormGroup.jsx
@@ -7,7 +7,9 @@ import {
} from '@edx/paragon';
const AuthnCustomValidationFormGroup = (props) => {
- const { onClick, onChange, onBlur } = props;
+ const {
+ onBlur, onChange, onClick, onFocus,
+ } = props;
const [showHelpText, setShowHelpText] = useState(false);
const [showLabelText, setShowLabelText] = useState(false);
@@ -31,6 +33,11 @@ const AuthnCustomValidationFormGroup = (props) => {
changeCb(e);
}
};
+ const onFocusHandler = (e, focusCb) => {
+ if (focusCb) {
+ focusCb(e);
+ }
+ };
const onOptionalHandler = (e, clickCb) => { clickCb(e); };
const showLabel = () => {
@@ -68,7 +75,7 @@ const AuthnCustomValidationFormGroup = (props) => {
inputProps.onChange = (e) => onChangeHandler(e, onChange);
inputProps.onClick = (e) => onClickHandler(e, onClick);
inputProps.onBlur = (e) => onBlurHandler(e, onBlur);
- inputProps.onFocus = (e) => onClickHandler(e, null);
+ inputProps.onFocus = (e) => onFocusHandler(e, onFocus);
if (props.type === 'select') {
inputProps.options = props.selectOptions;
@@ -122,6 +129,7 @@ AuthnCustomValidationFormGroup.defaultProps = {
onClick: null,
onBlur: null,
onChange: null,
+ onFocus: null,
isChecked: false,
checkboxMessage: '',
selectOptions: null,
@@ -147,6 +155,7 @@ AuthnCustomValidationFormGroup.propTypes = {
onClick: PropTypes.func,
onBlur: PropTypes.func,
onChange: PropTypes.func,
+ onFocus: PropTypes.func,
checkboxMessage: PropTypes.string,
selectOptions: PropTypes.arrayOf(PropTypes.shape({
key: PropTypes.string,
diff --git a/src/common-components/tests/AuthnValidationFormGroup.test.jsx b/src/common-components/tests/AuthnValidationFormGroup.test.jsx
index 88f3dfbf..e7e77895 100644
--- a/src/common-components/tests/AuthnValidationFormGroup.test.jsx
+++ b/src/common-components/tests/AuthnValidationFormGroup.test.jsx
@@ -22,7 +22,7 @@ describe('AuthnCustomValidationFormGroup', () => {
const validationFormGroup = mount();
validationFormGroup.find('input').simulate('focus');
- expect(validationFormGroup.find('label').prop('className')).toEqual('pt-10 h6 form-label');
+ expect(validationFormGroup.find('label').prop('className')).toEqual('pt-10 focus-out form-label');
});
it('should keep label hidden for checkbox field', () => {
diff --git a/src/register/RegistrationPage.jsx b/src/register/RegistrationPage.jsx
index 2834c789..aac16d3a 100644
--- a/src/register/RegistrationPage.jsx
+++ b/src/register/RegistrationPage.jsx
@@ -235,6 +235,12 @@ class RegistrationPage extends React.Component {
}
}
+ handleOnFocus(e) {
+ const { errors } = this.state;
+ errors[e.target.name] = '';
+ this.setState({ errors });
+ }
+
handleOnOptional(e) {
const optionalEnable = this.state.enableOptionalField;
const targetValue = e.target.id === 'additionalFields' ? !optionalEnable : e.target.checked;
@@ -479,6 +485,7 @@ class RegistrationPage extends React.Component {
value={this.state.name}
onBlur={(e) => this.handleOnBlur(e)}
onChange={(e) => this.handleOnChange(e)}
+ onFocus={(e) => this.handleOnFocus(e)}
helpText={intl.formatMessage(messages['helptext.name'])}
inputFieldStyle="border-gray-600"
/>
@@ -494,6 +501,7 @@ class RegistrationPage extends React.Component {
value={this.state.username}
onBlur={(e) => this.handleOnBlur(e)}
onChange={(e) => this.handleOnChange(e)}
+ onFocus={(e) => this.handleOnFocus(e)}
helpText={intl.formatMessage(messages['helptext.username'])}
inputFieldStyle="border-gray-600"
/>
@@ -509,6 +517,7 @@ class RegistrationPage extends React.Component {
value={this.state.email}
onBlur={(e) => this.handleOnBlur(e)}
onChange={(e) => this.handleOnChange(e)}
+ onFocus={(e) => this.handleOnFocus(e)}
helpText={intl.formatMessage(messages['helptext.email'])}
inputFieldStyle="border-gray-600"
/>
@@ -524,6 +533,7 @@ class RegistrationPage extends React.Component {
value={this.state.password}
onBlur={(e) => this.handleOnBlur(e)}
onChange={(e) => this.handleOnChange(e)}
+ onFocus={(e) => this.handleOnFocus(e)}
helpText={intl.formatMessage(messages['helptext.password'])}
inputFieldStyle="border-gray-600"
/>
@@ -541,6 +551,7 @@ class RegistrationPage extends React.Component {
value={this.state.country}
onBlur={(e) => this.handleOnBlur(e)}
onChange={(e) => this.handleOnChange(e)}
+ onFocus={(e) => this.handleOnFocus(e)}
selectOptions={this.getCountryOptions()}
inputFieldStyle="border-gray-600 custom-select-size"
/>
diff --git a/src/register/tests/RegistrationPage.test.jsx b/src/register/tests/RegistrationPage.test.jsx
index cf0c5307..d6961d6f 100644
--- a/src/register/tests/RegistrationPage.test.jsx
+++ b/src/register/tests/RegistrationPage.test.jsx
@@ -309,6 +309,29 @@ describe('RegistrationPageTests', () => {
expect(registrationPage.find('#validation-errors').first().text()).toEqual(alertBanner);
});
+ it('should clear field related error messages on input field Focus', () => {
+ const errors = {
+ email: '',
+ name: '',
+ username: '',
+ password: '',
+ country: '',
+ };
+ const registrationPage = mount(reduxWrapper());
+ registrationPage.find('button.btn-brand').simulate('click');
+
+ expect(registrationPage.find('#name-invalid-feedback').text()).toEqual(emptyFieldValidation.name);
+ registrationPage.find('input#name').simulate('focus');
+ expect(registrationPage.find('#username-invalid-feedback').text()).toEqual(emptyFieldValidation.username);
+ registrationPage.find('input#username').simulate('focus');
+ expect(registrationPage.find('#email-invalid-feedback').text()).toEqual(emptyFieldValidation.email);
+ registrationPage.find('input#email').simulate('focus');
+ expect(registrationPage.find('#password-invalid-feedback').text()).toEqual(emptyFieldValidation.password);
+ registrationPage.find('input#password').simulate('focus');
+ registrationPage.find('select#country').simulate('focus', { target: { value: 'US', name: 'country' } });
+ expect(registrationPage.find('RegistrationPage').state('errors')).toEqual(errors);
+ });
+
it('should show error message on alert and below the fields in case of 409', () => {
const errors = {
email: 'It looks like test@gmail.com belongs to an existing account. Try again with a different email address.',