From 5c18b94f881939c42e62fdea5924e49b855f0587 Mon Sep 17 00:00:00 2001 From: laviro <1ronlavi@gmail.com> Date: Wed, 6 Feb 2019 17:10:09 +0200 Subject: [PATCH] fix(LoginPage): remove inputs errors --- .../sass/patternfly-react/_login-page.scss | 2 +- .../components/LoginPage/LoginPage.stories.js | 205 +------- .../components/LoginPage/LoginPageFixtures.js | 473 ++++++++++++++++++ .../__snapshots__/LoginPage.test.js.snap | 3 + .../SocialLoginPage.test.js.snap | 10 +- .../LoginCardComponents/LoginCardForm.js | 21 +- .../LoginCardComponents/LoginCardInput.js | 31 +- .../LoginCardWithValidation.js | 195 ++++++-- .../LoginCardComponents/LoginFormError.js | 16 +- 9 files changed, 696 insertions(+), 260 deletions(-) create mode 100644 packages/patternfly-3/patternfly-react/src/components/LoginPage/LoginPageFixtures.js diff --git a/packages/patternfly-3/patternfly-react/sass/patternfly-react/_login-page.scss b/packages/patternfly-3/patternfly-react/sass/patternfly-react/_login-page.scss index 54ff5569891..562e9ce12b9 100644 --- a/packages/patternfly-3/patternfly-react/sass/patternfly-react/_login-page.scss +++ b/packages/patternfly-3/patternfly-react/sass/patternfly-react/_login-page.scss @@ -4,5 +4,5 @@ } .login-pf-input-warning { - margin-top: '5px'; + margin-top: 5px; } diff --git a/packages/patternfly-3/patternfly-react/src/components/LoginPage/LoginPage.stories.js b/packages/patternfly-3/patternfly-react/src/components/LoginPage/LoginPage.stories.js index a26a162bcb6..f4f3b078e38 100644 --- a/packages/patternfly-3/patternfly-react/src/components/LoginPage/LoginPage.stories.js +++ b/packages/patternfly-3/patternfly-react/src/components/LoginPage/LoginPage.stories.js @@ -1,14 +1,19 @@ import React from 'react'; import { storiesOf } from '@storybook/react'; import { withKnobs, number } from '@storybook/addon-knobs'; -import { action } from '@storybook/addon-actions'; import { defaultTemplate } from 'storybook/decorators/storyTemplates'; import { storybookPackageName, STORYBOOK_CATEGORY, DOCUMENTATION_URL } from 'storybook/constants/siteConstants'; import LoginPage from './LoginPage'; -import englishMessages from './mocks/messages.en'; -import frenchMessages from './mocks/messages.fr'; -import images from './assets/img'; + import { name } from '../../../package.json'; +import { + getManagedPageWithErrorsOnTopProps, + getManagedPageProps, + getBuildYourOwnPageProps, + createLogoList, + getManagedSocialLoginPageProps, + getBuildYourOwnSocialLoginPageProps +} from './LoginPageFixtures'; const stories = storiesOf( `${storybookPackageName(name)}/${STORYBOOK_CATEGORY.APPLICATION_FRAMEWORK}/Login Page`, @@ -23,196 +28,22 @@ stories.addDecorator( }) ); -const storyAction = (e, message) => { - e.preventDefault(); - action(message)(); -}; - -const createProps = () => { - const { header, footerLinks, card } = englishMessages; - footerLinks.forEach(link => { - link.onClick = e => storyAction(e, 'Footer Link was pressed'); - }); - return { - container: { - backgroundUrl: images.background, - translations: { en: englishMessages, fr: frenchMessages }, - className: '', - alert: { - message: header.alert, - onDismiss: e => storyAction(e, 'Notification was dismissed'), - show: true - } - }, - header: { - logoSrc: images.brand, - logoTitle: header.logo, - caption: header.caption - }, - footerLinks, - card: { - title: card.header.title, - selectedLanguage: card.header.selectedLanguage, - availableLanguages: card.header.availableLanguages, - signUp: { - label: card.signUp.label, - link: { - children: card.signUp.link.label, - href: '#', - onClick: e => storyAction(e, 'sign up was clicked') - } - }, - form: { - validate: true, - submitError: card.form.error, - showError: true, - usernameField: { - id: 'card_email', - type: 'email', - placeholder: card.usernameField.placeholder, - errors: card.usernameField.errors, - error: card.usernameField.errors.invalid, - showError: true - }, - passwordField: { - id: 'card_password', - type: 'password', - placeholder: card.passwordField.placeholder, - minLength: 8, - errors: card.passwordField.errors, - warnings: card.passwordField.warnings, - warning: card.passwordField.warnings.capsLock, - showWarning: true - }, - additionalFields: null, - rememberMe: { - label: card.rememberMe, - onClick: e => action('remember me checkbox was clicked')() - }, - forgotPassword: { - label: card.forgotPassword, - href: '#', - onClick: e => storyAction(e, 'Forgot password was clicked') - }, - submitText: card.form.submitText, - onSubmit: (e, onError) => { - onError(card.form.error); - storyAction(e, 'Form was submitted'); - } - }, - social: { - links: createLogoList() - } - } - }; -}; - -const createLogoList = () => { - const socialLinkClick = e => storyAction(e, 'Social Link was clicked'); - const { - google, - facebook, - linkedin, - github, - instagram, - stackExchange, - twitter, - git, - openID, - dropbox, - fedora, - skype - } = images; - return [ - { - src: google, - alt: 'Google', - text: 'Google', - onClick: e => socialLinkClick(e) - }, - { - src: facebook, - alt: 'Facebook', - text: 'Facebook', - onClick: e => socialLinkClick(e) - }, - { - src: linkedin, - alt: 'Linkedin', - text: 'Linkedin', - onClick: e => socialLinkClick(e) - }, - { - src: github, - alt: 'Github', - text: 'Github', - onClick: e => socialLinkClick(e) - }, - { - src: instagram, - alt: 'Instagram', - text: 'Instagram', - onClick: e => socialLinkClick(e) - }, - { - src: git, - alt: 'Git', - text: 'Git', - onClick: e => socialLinkClick(e) - }, - { - src: openID, - alt: 'OpenID', - text: 'OpenID', - onClick: e => socialLinkClick(e) - }, - { - src: dropbox, - alt: 'Dropbox', - text: 'Dropbox', - onClick: e => socialLinkClick(e) - }, - { - src: fedora, - alt: 'Fedora', - text: 'Fedora', - onClick: e => socialLinkClick(e) - }, - { - src: skype, - alt: 'Skype', - text: 'Skype', - onClick: e => socialLinkClick(e) - }, - { - src: twitter, - alt: 'Twitter', - text: 'Twitter', - onClick: e => socialLinkClick(e) - }, - { - src: stackExchange, - alt: 'StackExchange', - text: 'StackExchange', - onClick: e => socialLinkClick(e) - } - ]; -}; +stories.addWithInfo('Managed Login Page with errors display on top of the form', () => ( + +)); -stories.addWithInfo('Managed Basic Login Page', () => ); +stories.addWithInfo('Managed Login Page with errors display under form inputs', () => ( + +)); -stories.addWithInfo('Build Your own Basic Login Page', () => { - const props = { ...createProps() }; - props.card.form.validate = false; - return LoginPage.Pattern(props); -}); +stories.addWithInfo('Build Your own Basic Login Page', () => LoginPage.Pattern(getBuildYourOwnPageProps())); stories.addWithInfo('Managed Social Login Page', () => { const logoListCopy = createLogoList(); const listSize = number('Social List Size', 12); const socialLinks = logoListCopy.splice(0, listSize); - const props = { ...createProps() }; + const props = { ...getManagedSocialLoginPageProps() }; props.card.social.links = socialLinks; return ; @@ -223,7 +54,7 @@ stories.addWithInfo('Build Your own Social Login Page', () => { const listSize = number('Social List Size', 12); const socialLinks = logoListCopy.splice(0, listSize); - const props = { ...createProps() }; + const props = { ...getBuildYourOwnSocialLoginPageProps() }; props.card.social.links = socialLinks; props.card.form.validate = false; return LoginPage.Social.Pattern(props); diff --git a/packages/patternfly-3/patternfly-react/src/components/LoginPage/LoginPageFixtures.js b/packages/patternfly-3/patternfly-react/src/components/LoginPage/LoginPageFixtures.js new file mode 100644 index 00000000000..e9ebad3af85 --- /dev/null +++ b/packages/patternfly-3/patternfly-react/src/components/LoginPage/LoginPageFixtures.js @@ -0,0 +1,473 @@ +import englishMessages from './mocks/messages.en'; +import frenchMessages from './mocks/messages.fr'; +import images from './assets/img'; +// eslint-disable-next-line import/no-extraneous-dependencies +import { action } from '@storybook/addon-actions'; + +const storyAction = (e, message) => { + e.preventDefault(); + action(message)(); +}; + +export const createLogoList = () => { + const socialLinkClick = e => storyAction(e, 'Social Link was clicked'); + const { + google, + facebook, + linkedin, + github, + instagram, + stackExchange, + twitter, + git, + openID, + dropbox, + fedora, + skype + } = images; + return [ + { + src: google, + alt: 'Google', + text: 'Google', + onClick: e => socialLinkClick(e) + }, + { + src: facebook, + alt: 'Facebook', + text: 'Facebook', + onClick: e => socialLinkClick(e) + }, + { + src: linkedin, + alt: 'Linkedin', + text: 'Linkedin', + onClick: e => socialLinkClick(e) + }, + { + src: github, + alt: 'Github', + text: 'Github', + onClick: e => socialLinkClick(e) + }, + { + src: instagram, + alt: 'Instagram', + text: 'Instagram', + onClick: e => socialLinkClick(e) + }, + { + src: git, + alt: 'Git', + text: 'Git', + onClick: e => socialLinkClick(e) + }, + { + src: openID, + alt: 'OpenID', + text: 'OpenID', + onClick: e => socialLinkClick(e) + }, + { + src: dropbox, + alt: 'Dropbox', + text: 'Dropbox', + onClick: e => socialLinkClick(e) + }, + { + src: fedora, + alt: 'Fedora', + text: 'Fedora', + onClick: e => socialLinkClick(e) + }, + { + src: skype, + alt: 'Skype', + text: 'Skype', + onClick: e => socialLinkClick(e) + }, + { + src: twitter, + alt: 'Twitter', + text: 'Twitter', + onClick: e => socialLinkClick(e) + }, + { + src: stackExchange, + alt: 'StackExchange', + text: 'StackExchange', + onClick: e => socialLinkClick(e) + } + ]; +}; + +export const getManagedPageWithErrorsOnTopProps = () => { + const { header, footerLinks, card } = englishMessages; + footerLinks.forEach(link => { + link.onClick = e => storyAction(e, 'Footer Link was pressed'); + }); + return { + container: { + backgroundUrl: images.background, + translations: { en: englishMessages, fr: frenchMessages }, + className: '', + alert: { + message: header.alert, + onDismiss: e => storyAction(e, 'Notification was dismissed'), + show: true + } + }, + header: { + logoSrc: images.brand, + logoTitle: header.logo, + caption: header.caption + }, + footerLinks, + card: { + title: card.header.title, + selectedLanguage: card.header.selectedLanguage, + availableLanguages: card.header.availableLanguages, + signUp: { + label: card.signUp.label, + link: { + children: card.signUp.link.label, + href: '#', + onClick: e => storyAction(e, 'sign up was clicked') + } + }, + form: { + validate: true, + topErrorOnly: true, + usernameField: { + id: 'card_email', + type: 'email', + placeholder: card.usernameField.placeholder, + errors: card.usernameField.errors + }, + passwordField: { + id: 'card_password', + type: 'password', + placeholder: card.passwordField.placeholder, + minLength: 8, + errors: card.passwordField.errors, + warnings: card.passwordField.warnings + }, + additionalFields: null, + rememberMe: { + label: card.rememberMe, + onClick: e => action('remember me checkbox was clicked')() + }, + forgotPassword: { + label: card.forgotPassword, + href: '#', + onClick: e => storyAction(e, 'Forgot password was clicked') + }, + disableSubmit: false, + submitText: card.form.submitText, + onSubmit: (e, onError) => { + storyAction(e, 'Form was submitted successfully !'); + setTimeout(() => onError('Returning some server error'), 2000); + } + } + } + }; +}; + +export const getManagedPageProps = () => { + const { header, footerLinks, card } = englishMessages; + footerLinks.forEach(link => { + link.onClick = e => storyAction(e, 'Footer Link was pressed'); + }); + return { + container: { + backgroundUrl: images.background, + translations: { en: englishMessages, fr: frenchMessages }, + className: '', + alert: { + message: header.alert, + onDismiss: e => storyAction(e, 'Notification was dismissed'), + show: true + } + }, + header: { + logoSrc: images.brand, + logoTitle: header.logo, + caption: header.caption + }, + footerLinks, + card: { + title: card.header.title, + selectedLanguage: card.header.selectedLanguage, + availableLanguages: card.header.availableLanguages, + signUp: { + label: card.signUp.label, + link: { + children: card.signUp.link.label, + href: '#', + onClick: e => storyAction(e, 'sign up was clicked') + } + }, + form: { + validate: true, + usernameField: { + id: 'card_email', + type: 'email', + placeholder: card.usernameField.placeholder, + errors: card.usernameField.errors + }, + passwordField: { + id: 'card_password', + type: 'password', + placeholder: card.passwordField.placeholder, + minLength: 8, + errors: card.passwordField.errors, + warnings: card.passwordField.warnings + }, + additionalFields: null, + rememberMe: { + label: card.rememberMe, + onClick: e => action('remember me checkbox was clicked')() + }, + forgotPassword: { + label: card.forgotPassword, + href: '#', + onClick: e => storyAction(e, 'Forgot password was clicked') + }, + disableSubmit: false, + submitText: card.form.submitText, + onSubmit: (e, onError) => { + storyAction(e, 'Form was submitted successfully !'); + setTimeout(() => onError('Returning some server error'), 2000); + } + }, + social: { + links: createLogoList() + } + } + }; +}; + +export const getBuildYourOwnPageProps = () => { + const { header, footerLinks, card } = englishMessages; + footerLinks.forEach(link => { + link.onClick = e => storyAction(e, 'Footer Link was pressed'); + }); + return { + container: { + backgroundUrl: images.background, + translations: { en: englishMessages, fr: frenchMessages }, + className: '', + alert: { + message: header.alert, + onDismiss: e => storyAction(e, 'Notification was dismissed'), + show: true + } + }, + header: { + logoSrc: images.brand, + logoTitle: header.logo, + caption: header.caption + }, + footerLinks, + card: { + title: card.header.title, + selectedLanguage: card.header.selectedLanguage, + availableLanguages: card.header.availableLanguages, + signUp: { + label: card.signUp.label, + link: { + children: card.signUp.link.label, + href: '#', + onClick: e => storyAction(e, 'sign up was clicked') + } + }, + form: { + validate: false, + usernameField: { + id: 'card_email', + type: 'email', + placeholder: card.usernameField.placeholder, + errors: card.usernameField.errors + }, + passwordField: { + id: 'card_password', + type: 'password', + placeholder: card.passwordField.placeholder, + minLength: 8, + errors: card.passwordField.errors, + warnings: card.passwordField.warnings + }, + additionalFields: null, + rememberMe: { + label: card.rememberMe, + onClick: e => action('remember me checkbox was clicked')() + }, + forgotPassword: { + label: card.forgotPassword, + href: '#', + onClick: e => storyAction(e, 'Forgot password was clicked') + }, + disableSubmit: false, + submitText: card.form.submitText, + onSubmit: (e, onError) => { + storyAction(e, 'Form was submitted successfully !'); + setTimeout(() => onError('Returning some server error'), 2000); + } + } + } + }; +}; + +export const getManagedSocialLoginPageProps = () => { + const { header, footerLinks, card } = englishMessages; + footerLinks.forEach(link => { + link.onClick = e => storyAction(e, 'Footer Link was pressed'); + }); + return { + container: { + backgroundUrl: images.background, + translations: { en: englishMessages, fr: frenchMessages }, + className: '', + alert: { + message: header.alert, + onDismiss: e => storyAction(e, 'Notification was dismissed'), + show: true + } + }, + header: { + logoSrc: images.brand, + logoTitle: header.logo, + caption: header.caption + }, + footerLinks, + card: { + title: card.header.title, + selectedLanguage: card.header.selectedLanguage, + availableLanguages: card.header.availableLanguages, + signUp: { + label: card.signUp.label, + link: { + children: card.signUp.link.label, + href: '#', + onClick: e => storyAction(e, 'sign up was clicked') + } + }, + form: { + validate: true, + usernameField: { + id: 'card_email', + type: 'email', + placeholder: card.usernameField.placeholder, + errors: card.usernameField.errors + }, + passwordField: { + id: 'card_password', + type: 'password', + placeholder: card.passwordField.placeholder, + minLength: 8, + errors: card.passwordField.errors, + warnings: card.passwordField.warnings + }, + additionalFields: null, + rememberMe: { + label: card.rememberMe, + onClick: e => action('remember me checkbox was clicked')() + }, + forgotPassword: { + label: card.forgotPassword, + href: '#', + onClick: e => storyAction(e, 'Forgot password was clicked') + }, + disableSubmit: false, + submitText: card.form.submitText, + onSubmit: (e, onError) => { + storyAction(e, 'Form was submitted successfully !'); + setTimeout(() => onError('Returning some server error'), 2000); + } + }, + social: { + links: createLogoList() + } + } + }; +}; + +export const getBuildYourOwnSocialLoginPageProps = () => { + const { header, footerLinks, card } = englishMessages; + footerLinks.forEach(link => { + link.onClick = e => storyAction(e, 'Footer Link was pressed'); + }); + return { + container: { + backgroundUrl: images.background, + translations: { en: englishMessages, fr: frenchMessages }, + className: '', + alert: { + message: header.alert, + onDismiss: e => storyAction(e, 'Notification was dismissed'), + show: true + } + }, + header: { + logoSrc: images.brand, + logoTitle: header.logo, + caption: header.caption + }, + footerLinks, + card: { + title: card.header.title, + selectedLanguage: card.header.selectedLanguage, + availableLanguages: card.header.availableLanguages, + signUp: { + label: card.signUp.label, + link: { + children: card.signUp.link.label, + href: '#', + onClick: e => storyAction(e, 'sign up was clicked') + } + }, + form: { + validate: false, + submitError: card.form.error, + showError: true, + usernameField: { + id: 'card_email', + type: 'email', + placeholder: card.usernameField.placeholder, + errors: card.usernameField.errors, + error: card.usernameField.errors.invalid, + showError: true + }, + passwordField: { + id: 'card_password', + type: 'password', + placeholder: card.passwordField.placeholder, + minLength: 8, + errors: card.passwordField.errors, + warnings: card.passwordField.warnings, + warning: card.passwordField.warnings.capsLock, + showWarning: true + }, + additionalFields: null, + rememberMe: { + label: card.rememberMe, + onClick: e => action('remember me checkbox was clicked')() + }, + forgotPassword: { + label: card.forgotPassword, + href: '#', + onClick: e => storyAction(e, 'Forgot password was clicked') + }, + disableSubmit: false, + submitText: card.form.submitText, + onSubmit: (e, onError) => { + storyAction(e, 'Form was submitted successfully !'); + setTimeout(() => onError('Returning some server error'), 2000); + } + }, + social: { + links: createLogoList() + } + } + }; +}; diff --git a/packages/patternfly-3/patternfly-react/src/components/LoginPage/__snapshots__/LoginPage.test.js.snap b/packages/patternfly-3/patternfly-react/src/components/LoginPage/__snapshots__/LoginPage.test.js.snap index 1602e14a611..22207a1b585 100644 --- a/packages/patternfly-3/patternfly-react/src/components/LoginPage/__snapshots__/LoginPage.test.js.snap +++ b/packages/patternfly-3/patternfly-react/src/components/LoginPage/__snapshots__/LoginPage.test.js.snap @@ -125,6 +125,9 @@ exports[`Component matches snapshot 1`] = ` class="" novalidate="" > +