@thecb/components 2.2.1 → 2.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (70) hide show
  1. package/.tool-versions +1 -0
  2. package/dist/index.cjs.js +30904 -3033
  3. package/package.json +15 -35
  4. package/rollup.config.js +3 -1
  5. package/src/components/atoms/button-with-action/ButtonWithAction.js +25 -4
  6. package/src/components/atoms/button-with-action/ButtonWithAction.theme.js +64 -234
  7. package/src/components/atoms/formatted-credit-card/FormattedCreditCard.js +53 -0
  8. package/src/components/atoms/formatted-credit-card/FormattedCreditCard.theme.js +9 -0
  9. package/src/components/atoms/formatted-credit-card/index.js +3 -0
  10. package/src/components/atoms/icons/AccountNumberImage.js +95 -0
  11. package/src/components/atoms/icons/BankIcon.js +82 -0
  12. package/src/components/atoms/icons/CheckmarkIcon.js +55 -0
  13. package/src/components/atoms/icons/GenericCard.js +39 -0
  14. package/src/components/atoms/icons/PaymentIcon.js +50 -0
  15. package/src/components/atoms/icons/RoutingNumberImage.js +95 -0
  16. package/src/components/atoms/icons/index.js +14 -1
  17. package/src/components/atoms/index.js +3 -0
  18. package/src/components/atoms/jumbo/Jumbo.js +76 -0
  19. package/src/components/atoms/jumbo/index.js +3 -0
  20. package/src/components/atoms/loading/Loading.js +17 -0
  21. package/src/components/atoms/loading/index.js +3 -0
  22. package/src/components/atoms/nav-header/NavHeader.js +1 -1
  23. package/src/components/index.js +1 -0
  24. package/src/components/molecules/account-and-routing-modal/AccountAndRoutingModal.js +75 -0
  25. package/src/components/molecules/account-and-routing-modal/AccountAndRoutingModal.theme.js +24 -0
  26. package/src/components/molecules/account-and-routing-modal/index.js +3 -0
  27. package/src/components/molecules/address-form/AddressForm.js +2 -1
  28. package/src/components/molecules/address-form/index.js +6 -6
  29. package/src/components/molecules/change-password-form/ChangePasswordForm.js +2 -1
  30. package/src/components/molecules/change-password-form/index.js +1 -1
  31. package/src/components/molecules/edit-name-form/EditNameForm.js +2 -1
  32. package/src/components/molecules/edit-name-form/index.js +1 -1
  33. package/src/components/molecules/editable-list/EditableList.js +139 -0
  34. package/src/components/molecules/editable-list/EditableList.styled.js +31 -0
  35. package/src/components/molecules/editable-list/index.js +3 -0
  36. package/src/components/molecules/editable-table/EditableTable.js +30 -0
  37. package/src/components/molecules/editable-table/EditableTable.styled.js +80 -0
  38. package/src/components/molecules/editable-table/TableListItem.js +64 -0
  39. package/src/components/molecules/editable-table/index.js +4 -0
  40. package/src/components/molecules/email-form/EmailForm.js +2 -1
  41. package/src/components/molecules/email-form/index.js +1 -1
  42. package/src/components/molecules/forgot-password-form/ForgotPasswordForm.js +2 -1
  43. package/src/components/molecules/forgot-password-form/index.js +1 -1
  44. package/src/components/molecules/index.js +5 -0
  45. package/src/components/molecules/login-form/LoginForm.js +2 -1
  46. package/src/components/molecules/login-form/index.js +1 -1
  47. package/src/components/molecules/module/Module.js +1 -3
  48. package/src/components/molecules/partial-amount-form/PartialAmountForm.js +73 -0
  49. package/src/components/molecules/partial-amount-form/PartialAmountForm.state.js +51 -0
  50. package/src/components/molecules/partial-amount-form/index.js +4 -0
  51. package/src/components/molecules/payment-form-ach/PaymentFormACH.js +189 -0
  52. package/src/components/molecules/payment-form-ach/PaymentFormACH.state.js +38 -0
  53. package/src/components/molecules/payment-form-ach/index.js +11 -0
  54. package/src/components/molecules/payment-form-card/PaymentFormCard.js +132 -0
  55. package/src/components/molecules/payment-form-card/PaymentFormCard.state.js +39 -0
  56. package/src/components/molecules/payment-form-card/index.js +11 -0
  57. package/src/components/molecules/phone-form/PhoneForm.js +2 -1
  58. package/src/components/molecules/phone-form/index.js +1 -1
  59. package/src/components/molecules/registration-form/RegistrationForm.js +2 -1
  60. package/src/components/molecules/registration-form/index.js +1 -1
  61. package/src/components/molecules/reset-password-form/ResetPasswordForm.js +3 -1
  62. package/src/components/molecules/reset-password-form/index.js +1 -1
  63. package/src/constants/index.js +2 -0
  64. package/src/index.js +2 -1
  65. package/src/util/formats.js +54 -2
  66. package/src/util/general.js +27 -4
  67. package/src/util/index.js +2 -0
  68. package/src/util/inputValidationUtils.js +0 -167
  69. package/stats.html +2652 -0
  70. package/src/util/router-utils.js +0 -23
@@ -1,13 +1,14 @@
1
1
  import React, { useEffect } from "react";
2
2
  import { required, isProbablyEmail } from "redux-freeform";
3
3
  import { FormInput, FormInputColumn } from "../../atoms/form-layouts";
4
+ import { noop } from "../../../util/general";
4
5
 
5
6
  const LoginForm = ({
6
7
  clearOnDismount,
7
8
  fields,
8
9
  actions,
9
10
  showErrors,
10
- handleSubmit
11
+ handleSubmit = noop
11
12
  }) => {
12
13
  if (clearOnDismount) {
13
14
  useEffect(() => () => actions.form.clear(), []);
@@ -2,7 +2,7 @@ import LoginForm from "./LoginForm";
2
2
  import {
3
3
  reducer,
4
4
  mapStateToProps,
5
- mapDispatchToProps,
5
+ mapDispatchToProps
6
6
  } from "./LoginForm.state";
7
7
 
8
8
  LoginForm.reducer = reducer;
@@ -1,8 +1,6 @@
1
- import React from "react";
2
-
1
+ import React, { Fragment } from "react";
3
2
  import Heading from "../../atoms/heading";
4
3
  import { Box } from "../../atoms/layouts";
5
- import { Fragment } from "react";
6
4
 
7
5
  const Module = ({
8
6
  heading,
@@ -0,0 +1,73 @@
1
+ import React from "react";
2
+ import { required, numberGreaterThan, numberLessThan } from "redux-freeform";
3
+ import { displayCurrency } from "../../../util/general";
4
+ import Text from "../../atoms/text";
5
+ import {
6
+ FormInput,
7
+ FormInputColumn,
8
+ FormContainer
9
+ } from "../../atoms/form-layouts";
10
+ import { moneyFormat } from "../../../util/formats";
11
+
12
+ const PartialAmountForm = ({
13
+ variant = "default",
14
+ lineItems,
15
+ maximum,
16
+ minimum = 1,
17
+ clearOnDismount,
18
+ fields,
19
+ actions,
20
+ showErrors = false
21
+ }) => {
22
+ if (clearOnDismount) {
23
+ useEffect(() => () => actions.form.clear(), []);
24
+ }
25
+
26
+ const amountErrors = {
27
+ [required.error]: "Amount is required",
28
+ [numberGreaterThan.error]: `Your total payment must be greater than ${displayCurrency(
29
+ minimum
30
+ )}`,
31
+ [numberLessThan.error]: `Your total payment must be less than ${displayCurrency(
32
+ maximum
33
+ )}`
34
+ };
35
+
36
+ const lineItemsNew = Array.isArray(lineItems) ? lineItems : [];
37
+ return (
38
+ <FormContainer variant={variant} role="form" aria-label="Partial amount">
39
+ <Text variant="p">
40
+ Pay a portion of your current bill. The remaining balance will still be
41
+ due on the same due date.
42
+ </Text>
43
+ <div style={{ height: "16px" }}></div>
44
+ <FormInputColumn>
45
+ {lineItemsNew.map(li => (
46
+ <FormInput
47
+ labelTextWhenNoError={li.description}
48
+ key={li.id}
49
+ field={fields[li.id]}
50
+ fieldActions={actions.fields[li.id]}
51
+ showErrors={showErrors}
52
+ errorMessages={amountErrors}
53
+ style={{ textAlign: "right" }}
54
+ placeholder="$0.00"
55
+ formatter={moneyFormat}
56
+ decorator={
57
+ <Text variant="p">
58
+ Amount owed:{" "}
59
+ {
60
+ <Text variant="p" weight="600">
61
+ {displayCurrency(li.amount)}
62
+ </Text>
63
+ }
64
+ </Text>
65
+ }
66
+ />
67
+ ))}
68
+ </FormInputColumn>
69
+ </FormContainer>
70
+ );
71
+ };
72
+
73
+ export default PartialAmountForm;
@@ -0,0 +1,51 @@
1
+ import {
2
+ createFormState,
3
+ required,
4
+ onlyNaturals,
5
+ validateSum,
6
+ numberGreaterThan,
7
+ numberLessThan
8
+ } from "redux-freeform";
9
+
10
+ export const createPartialAmountFormState = (
11
+ lineItems,
12
+ maximum,
13
+ minimum = 1
14
+ ) => {
15
+ const formConfig = lineItems.reduce((acc, item) => {
16
+ const validators = [
17
+ required(),
18
+ validateSum(
19
+ numberGreaterThan(minimum),
20
+ lineItems
21
+ .filter(lineItem => lineItem != item)
22
+ .reduce((acc, curr) => [...acc, curr.id], [])
23
+ )
24
+ ];
25
+ if (!!maximum) {
26
+ validators.push(
27
+ validateSum(
28
+ numberLessThan(maximum),
29
+ lineItems
30
+ .filter(lineItem => lineItem != item)
31
+ .reduce((acc, curr) => [...acc, curr.id], [])
32
+ )
33
+ );
34
+ }
35
+ return {
36
+ ...acc,
37
+ [item.id]: {
38
+ validators: validators,
39
+ constraints: [onlyNaturals()]
40
+ }
41
+ };
42
+ }, {});
43
+ const { reducer, mapStateToProps, mapDispatchToProps } = createFormState(
44
+ formConfig
45
+ );
46
+ return {
47
+ partialAmountFormReducer: reducer,
48
+ partialAmountFormMapStateToProps: mapStateToProps,
49
+ partialAmountFormMapDispatchToProps: mapDispatchToProps
50
+ };
51
+ };
@@ -0,0 +1,4 @@
1
+ import PartialAmountForm from "./PartialAmountForm";
2
+ import { createPartialAmountFormState } from "./PartialAmountForm.state";
3
+
4
+ export { PartialAmountForm, createPartialAmountFormState };
@@ -0,0 +1,189 @@
1
+ import React, { useEffect, useState } from "react";
2
+ import styled from "styled-components";
3
+ import { ifElse, isNil, always } from "ramda";
4
+ import Checkbox from "../../atoms/checkbox";
5
+ import {
6
+ required,
7
+ matchesField,
8
+ hasLength,
9
+ isRoutingNumber
10
+ } from "redux-freeform";
11
+ import FormSelect from "../../atoms/form-select";
12
+ import {
13
+ FormInput,
14
+ FormInputColumn,
15
+ FormContainer
16
+ } from "../../atoms/form-layouts";
17
+ import Alert from "../../atoms/alert";
18
+ import AccountAndRoutingModal from "../account-and-routing-modal";
19
+ import { displayCurrency, noop } from "../../../util/general";
20
+
21
+ const ModalWrapper = styled.div``;
22
+
23
+ const PaymentFormACH = ({
24
+ variant = "default",
25
+ defaultMethod,
26
+ toggleCheckbox,
27
+ hideDefaultPayment = true,
28
+ allowBankAccountType,
29
+ clearOnDismount,
30
+ fields,
31
+ actions,
32
+ showErrors,
33
+ fees,
34
+ handleSubmit = noop
35
+ }) => {
36
+ if (clearOnDismount) {
37
+ useEffect(() => () => actions.form.clear(), []);
38
+ }
39
+ const [showRouting, toggleShowRouting] = useState(false);
40
+ const [showAccount, toggleShowAccount] = useState(false);
41
+
42
+ const nameErrors = {
43
+ [required.error]: "Name is required"
44
+ };
45
+ const routingNumberErrors = {
46
+ [required.error]: "Routing number is required",
47
+ [hasLength.error]: "Routing number must be 9 digits",
48
+ [isRoutingNumber.error]: "Invalid routing number"
49
+ };
50
+ const confirmRoutingNumberErrors = {
51
+ [matchesField.error]:
52
+ "Confirm routing number field must match routing number"
53
+ };
54
+ const accountNumberErrors = {
55
+ [required.error]: "Account number is required",
56
+ [hasLength.error]: "Account number must be between 6 and 17 digits"
57
+ };
58
+ const confirmAccountNumberErrors = {
59
+ [matchesField.error]:
60
+ "Confirm account number field must match account number"
61
+ };
62
+ const accountTypeErrors = {
63
+ [required.error]: "Account type is required"
64
+ };
65
+
66
+ return (
67
+ <FormContainer variant={variant} role="form" aria-label="ACH Payment">
68
+ <FormInputColumn>
69
+ <FormInput
70
+ labelTextWhenNoError="Name on bank account"
71
+ errorMessages={nameErrors}
72
+ field={fields.name}
73
+ fieldActions={actions.fields.name}
74
+ showErrors={showErrors}
75
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
76
+ />
77
+ <FormInput
78
+ labelTextWhenNoError="Routing number"
79
+ errorMessages={routingNumberErrors}
80
+ field={fields.routingNumber}
81
+ fieldActions={actions.fields.routingNumber}
82
+ showErrors={showErrors}
83
+ helperModal={() => (
84
+ <ModalWrapper
85
+ tabIndex="0"
86
+ onKeyDown={e =>
87
+ e.key === "Enter" && toggleShowAccount(!showRouting)
88
+ }
89
+ >
90
+ <AccountAndRoutingModal
91
+ link="What is this?"
92
+ title="Where is my routing number?"
93
+ content="Your routing number is the 9-digit number in the bottom left
94
+ corner of your check."
95
+ imageType="Routing"
96
+ isOpen={showRouting}
97
+ toggleOpen={toggleShowRouting}
98
+ />
99
+ </ModalWrapper>
100
+ )}
101
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
102
+ />
103
+ <FormInput
104
+ labelTextWhenNoError="Confirm routing number"
105
+ errorMessages={confirmRoutingNumberErrors}
106
+ field={fields.confirmRoutingNumber}
107
+ fieldActions={actions.fields.confirmRoutingNumber}
108
+ showErrors={showErrors}
109
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
110
+ />
111
+ <FormInput
112
+ labelTextWhenNoError="Account number"
113
+ errorMessages={accountNumberErrors}
114
+ field={fields.accountNumber}
115
+ fieldActions={actions.fields.accountNumber}
116
+ showErrors={showErrors}
117
+ helperModal={() => (
118
+ <ModalWrapper
119
+ tabIndex="0"
120
+ onKeyDown={e =>
121
+ e.key === "Enter" && toggleShowAccount(!showAccount)
122
+ }
123
+ >
124
+ <AccountAndRoutingModal
125
+ link="What is this?"
126
+ title="Where is my account number?"
127
+ content="Your account number is usually the 10-digit number in the bottom
128
+ of your check to the right of the routing number."
129
+ imageType="Account"
130
+ isOpen={showAccount}
131
+ toggleOpen={toggleShowAccount}
132
+ />
133
+ </ModalWrapper>
134
+ )}
135
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
136
+ />
137
+ <FormInput
138
+ labelTextWhenNoError="Confirm account number"
139
+ errorMessages={confirmAccountNumberErrors}
140
+ field={fields.confirmAccountNumber}
141
+ fieldActions={actions.fields.confirmAccountNumber}
142
+ showErrors={showErrors}
143
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
144
+ />
145
+ {allowBankAccountType && (
146
+ <FormSelect
147
+ labelTextWhenNoError="Account type"
148
+ options={[
149
+ { text: "Select account type", value: "" },
150
+ { text: "Checking", value: "CHECKING" },
151
+ { text: "Savings", value: "SAVINGS" }
152
+ ]}
153
+ fieldActions={actions.fields.accountType}
154
+ showErrors={showErrors}
155
+ errorMessages={accountTypeErrors}
156
+ field={fields.accountType}
157
+ />
158
+ )}
159
+ {!hideDefaultPayment && (
160
+ <Checkbox
161
+ title="Save as Default Payment Method"
162
+ name="default-payment-ach"
163
+ onChange={toggleCheckbox}
164
+ checked={defaultMethod.value}
165
+ hidden={hideDefaultPayment}
166
+ />
167
+ )}
168
+ {!!fees?.value && (
169
+ <Alert
170
+ heading="Processing Fee"
171
+ text={`There is a processing fee of ${
172
+ fees.type === "FLAT"
173
+ ? `${displayCurrency(fees.value)}`
174
+ : `${fees.value * 100}%`
175
+ } ${ifElse(
176
+ isNil,
177
+ always(""),
178
+ a => `with a minimum of ${displayCurrency(a)} `
179
+ )(fees.minimumInCents)}on all bank account payments.`}
180
+ variant="info"
181
+ showQuitLink={false}
182
+ />
183
+ )}
184
+ </FormInputColumn>
185
+ </FormContainer>
186
+ );
187
+ };
188
+
189
+ export default PaymentFormACH;
@@ -0,0 +1,38 @@
1
+ import {
2
+ createFormState,
3
+ required,
4
+ matchesField,
5
+ onlyIntegers,
6
+ hasLength,
7
+ isRoutingNumber
8
+ } from "redux-freeform";
9
+
10
+ const formConfig = {
11
+ name: {
12
+ validators: [required()]
13
+ },
14
+ routingNumber: {
15
+ validators: [required(), hasLength(9, 9), isRoutingNumber()],
16
+ constraints: [onlyIntegers(), hasLength(0, 9)]
17
+ },
18
+ confirmRoutingNumber: {
19
+ validators: [matchesField("routingNumber")],
20
+ constraints: [onlyIntegers(), hasLength(0, 9)]
21
+ },
22
+ accountNumber: {
23
+ validators: [required(), hasLength(6, 17)],
24
+ constraints: [onlyIntegers(), hasLength(0, 17)]
25
+ },
26
+ confirmAccountNumber: {
27
+ validators: [matchesField("accountNumber")],
28
+ constraints: [onlyIntegers(), hasLength(0, 17)]
29
+ },
30
+ accountType: {
31
+ defaultValue: "CHECKING",
32
+ validators: [required()]
33
+ }
34
+ };
35
+
36
+ export const { reducer, mapStateToProps, mapDispatchToProps } = createFormState(
37
+ formConfig
38
+ );
@@ -0,0 +1,11 @@
1
+ import PaymentFormACH from "./PaymentFormACH";
2
+ import {
3
+ reducer,
4
+ mapStateToProps,
5
+ mapDispatchToProps
6
+ } from "./PaymentFormACH.state";
7
+
8
+ PaymentFormACH.reducer = reducer;
9
+ PaymentFormACH.mapStateToProps = mapStateToProps;
10
+ PaymentFormACH.mapDispatchToProps = mapDispatchToProps;
11
+ export default PaymentFormACH;
@@ -0,0 +1,132 @@
1
+ import React, { useEffect } from "react";
2
+ import { required, hasLength, matchesRegex } from "redux-freeform";
3
+ import { ifElse, isNil, always } from "ramda";
4
+ import { checkCardBrand, displayCurrency, noop } from "../../../util/general";
5
+ import { expirationDateFormat, creditCardFormat } from "../../../util/formats";
6
+ import {
7
+ FormInput,
8
+ FormInputColumn,
9
+ FormContainer,
10
+ FormInputRow
11
+ } from "../../atoms/form-layouts";
12
+ import { Box } from "../../atoms/layouts";
13
+ import Alert from "../../atoms/alert";
14
+
15
+ const nameOnCardErrors = {
16
+ [required.error]: "Name is required"
17
+ };
18
+ const creditCardNumberErrors = {
19
+ [required.error]: "Credit card number is required",
20
+ [hasLength.error]: "Credit card number is invalid"
21
+ };
22
+ const expirationDateErrors = {
23
+ [required.error]: "Expiration date is required",
24
+ [hasLength.error]: "Expiration date is invalid",
25
+ [matchesRegex.error]: "Expiration date is invalid"
26
+ };
27
+ const cvvErrors = {
28
+ [required.error]: "CVV is required",
29
+ [hasLength.error]: "CVV is invalid"
30
+ };
31
+ const zipCodeErrors = {
32
+ [required.error]: "Zip code is required",
33
+ [hasLength.error]: "Zip code is invalid"
34
+ };
35
+
36
+ const PaymentFormCard = ({
37
+ variant = "default",
38
+ hideZipCode = false,
39
+ clearOnDismount,
40
+ fields,
41
+ actions,
42
+ showErrors,
43
+ fees,
44
+ handleSubmit = noop,
45
+ isMobile
46
+ }) => {
47
+ useEffect(() => {
48
+ if (clearOnDismount) {
49
+ return () => actions.form.clear();
50
+ }
51
+ }, []);
52
+ return (
53
+ <FormContainer variant={variant} role="form" aria-label="Card payment">
54
+ <FormInputColumn>
55
+ <FormInput
56
+ labelTextWhenNoError="Name on card"
57
+ errorMessages={nameOnCardErrors}
58
+ field={fields.nameOnCard}
59
+ fieldActions={actions.fields.nameOnCard}
60
+ showErrors={showErrors}
61
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
62
+ />
63
+ <FormInput
64
+ labelTextWhenNoError="Credit card number"
65
+ errorMessages={creditCardNumberErrors}
66
+ field={fields.creditCardNumber}
67
+ fieldActions={actions.fields.creditCardNumber}
68
+ showErrors={showErrors}
69
+ formatter={creditCardFormat}
70
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
71
+ />
72
+ <FormInputRow breakpoint="20rem">
73
+ <FormInput
74
+ labelTextWhenNoError="Expiration date (MM/YY)"
75
+ errorMessages={expirationDateErrors}
76
+ field={fields.expirationDate}
77
+ fieldActions={actions.fields.expirationDate}
78
+ showErrors={showErrors}
79
+ formatter={expirationDateFormat}
80
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
81
+ />
82
+ <FormInput
83
+ labelTextWhenNoError="CVV"
84
+ errorMessages={cvvErrors}
85
+ field={fields.cvv}
86
+ fieldActions={actions.fields.cvv}
87
+ showErrors={showErrors}
88
+ background={
89
+ checkCardBrand(fields.creditCardNumber.rawValue) == "AMEX"
90
+ ? "/AmexCVVHint.svg"
91
+ : "/CVVHint.svg"
92
+ }
93
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
94
+ />
95
+ </FormInputRow>
96
+ {!hideZipCode && (
97
+ <Box
98
+ padding={isMobile ? "0" : "0 0.5rem 0 0"}
99
+ width={isMobile ? "100%" : "50%"}
100
+ >
101
+ <FormInput
102
+ labelTextWhenNoError="Zip code"
103
+ errorMessages={zipCodeErrors}
104
+ field={fields.zipCode}
105
+ fieldActions={actions.fields.zipCode}
106
+ showErrors={showErrors}
107
+ onKeyDown={e => e.key === "Enter" && handleSubmit(e)}
108
+ />
109
+ </Box>
110
+ )}
111
+ {!!fees?.value && (
112
+ <Alert
113
+ heading="Processing Fee"
114
+ text={`There is a processing fee of ${
115
+ fees.type === "FLAT"
116
+ ? `${displayCurrency(fees.value)}`
117
+ : `${fees.value * 100}%`
118
+ } ${ifElse(
119
+ isNil,
120
+ always(""),
121
+ a => `with a minimum of ${displayCurrency(a)} `
122
+ )(fees.minimumInCents)} on all card payments.`}
123
+ variant="info"
124
+ showQuitLink={false}
125
+ />
126
+ )}
127
+ </FormInputColumn>
128
+ </FormContainer>
129
+ );
130
+ };
131
+
132
+ export default PaymentFormCard;
@@ -0,0 +1,39 @@
1
+ import {
2
+ createFormState,
3
+ required,
4
+ onlyIntegers,
5
+ hasLength,
6
+ matchesRegex
7
+ } from "redux-freeform";
8
+
9
+ //TODO: Will make zip code able to have more than 5 digits once we add in the FormattedInput because it will have issues with format of 60606-1111.
10
+
11
+ const formConfig = {
12
+ nameOnCard: {
13
+ validators: [required()]
14
+ },
15
+ creditCardNumber: {
16
+ validators: [required(), hasLength(15, 16)],
17
+ constraints: [onlyIntegers(), hasLength(0, 16)]
18
+ },
19
+ expirationDate: {
20
+ validators: [
21
+ required(),
22
+ hasLength(4, 4),
23
+ matchesRegex(/^(01|02|03|04|05|06|07|08|09|10|11|12)[2-9]\d$/)
24
+ ],
25
+ constraints: [onlyIntegers(), hasLength(0, 4)]
26
+ },
27
+ cvv: {
28
+ validators: [required(), hasLength(3, 4)],
29
+ constraints: [onlyIntegers(), hasLength(0, 4)]
30
+ },
31
+ zipCode: {
32
+ validators: [required(), hasLength(5, 5)],
33
+ constraints: [onlyIntegers(), hasLength(0, 5)]
34
+ }
35
+ };
36
+
37
+ export const { reducer, mapStateToProps, mapDispatchToProps } = createFormState(
38
+ formConfig
39
+ );
@@ -0,0 +1,11 @@
1
+ import PaymentFormCard from "./PaymentFormCard";
2
+ import {
3
+ reducer,
4
+ mapStateToProps,
5
+ mapDispatchToProps
6
+ } from "./PaymentFormCard.state";
7
+
8
+ PaymentFormCard.reducer = reducer;
9
+ PaymentFormCard.mapStateToProps = mapStateToProps;
10
+ PaymentFormCard.mapDispatchToProps = mapDispatchToProps;
11
+ export default PaymentFormCard;
@@ -7,6 +7,7 @@ import {
7
7
  FormContainer,
8
8
  FormInputColumn
9
9
  } from "../../atoms/form-layouts";
10
+ import { noop } from "../../../util/general";
10
11
 
11
12
  const PhoneForm = ({
12
13
  variant = "default",
@@ -14,7 +15,7 @@ const PhoneForm = ({
14
15
  actions,
15
16
  clearOnDismount,
16
17
  showErrors,
17
- handleSubmit
18
+ handleSubmit = noop
18
19
  }) => {
19
20
  if (clearOnDismount) {
20
21
  useEffect(() => () => actions.form.clear(), []);
@@ -2,7 +2,7 @@ import PhoneForm from "./PhoneForm";
2
2
  import {
3
3
  reducer,
4
4
  mapStateToProps,
5
- mapDispatchToProps,
5
+ mapDispatchToProps
6
6
  } from "./PhoneForm.state";
7
7
 
8
8
  PhoneForm.reducer = reducer;
@@ -12,12 +12,13 @@ import {
12
12
  import PasswordRequirements from "../../atoms/password-requirements";
13
13
  import { Box } from "../../atoms/layouts";
14
14
  import { FormInput, FormInputColumn } from "../../atoms/form-layouts";
15
+ import { noop } from "../../../util/general";
15
16
 
16
17
  const RegistrationForm = ({
17
18
  clearOnDismount,
18
19
  fields,
19
20
  actions,
20
- handleSubmit,
21
+ handleSubmit = noop,
21
22
  showErrors,
22
23
  isMobile
23
24
  }) => {
@@ -2,7 +2,7 @@ import RegistrationForm from "./RegistrationForm";
2
2
  import {
3
3
  reducer,
4
4
  mapStateToProps,
5
- mapDispatchToProps,
5
+ mapDispatchToProps
6
6
  } from "./RegistrationForm.state";
7
7
 
8
8
  RegistrationForm.reducer = reducer;
@@ -11,8 +11,10 @@ import {
11
11
  import PasswordRequirements from "../../atoms/password-requirements";
12
12
  import { Box } from "../../atoms/layouts";
13
13
  import { FormInput, FormInputColumn } from "../../atoms/form-layouts";
14
+ import { noop } from "../../../util/general";
15
+
14
16
  const ResetPasswordForm = ({
15
- handleSubmit,
17
+ handleSubmit = noop,
16
18
  clearOnDismount,
17
19
  fields,
18
20
  actions,
@@ -2,7 +2,7 @@ import ResetPasswordForm from "./ResetPasswordForm";
2
2
  import {
3
3
  reducer,
4
4
  mapStateToProps,
5
- mapDispatchToProps,
5
+ mapDispatchToProps
6
6
  } from "./ResetPasswordForm.state";
7
7
 
8
8
  ResetPasswordForm.reducer = reducer;
@@ -0,0 +1,2 @@
1
+ export * from "./colors";
2
+ export * from "./style_constants";
package/src/index.js CHANGED
@@ -1,2 +1,3 @@
1
- // export * from "./deprecated";
2
1
  export * from "./components";
2
+ export * from "./constants";
3
+ export * from "./util";