From c6680b391c04fb2ead4d2f794ca9a46903d11ae5 Mon Sep 17 00:00:00 2001 From: Eran Machiels Date: Sun, 31 Jan 2021 22:21:07 +0100 Subject: [PATCH 01/10] Added dirty flag --- __tests__/suits/Area.test.tsx | 18 ++++++++++++++++ __tests__/suits/Provider.test.tsx | 20 ++++++++++++++++++ src/AreaScope.ts | 4 ++++ src/ProviderScope.ts | 4 ++++ src/components/ValidatorArea.tsx | 3 ++- src/components/ValidatorProvider.tsx | 31 +++++++++++++++++++--------- 6 files changed, 69 insertions(+), 11 deletions(-) diff --git a/__tests__/suits/Area.test.tsx b/__tests__/suits/Area.test.tsx index 08700d9..b241374 100644 --- a/__tests__/suits/Area.test.tsx +++ b/__tests__/suits/Area.test.tsx @@ -320,5 +320,23 @@ describe('test ValidatorProvider', () => { area.find('input').at(0).simulate('blur'); await tick(); expect(logFn).toHaveBeenCalled(); + }); + + it('should indicate whether the area is dirty', async () => { + const area = mount( + + {({ dirty }) => ( + <> + +
{dirty ? 'yes' : 'no'}
+ + )} +
+ ); + + area.find('input').at(0).simulate('blur'); + await tick(); + expect(area.find('div').text()).toBe('yes'); + }) }) diff --git a/__tests__/suits/Provider.test.tsx b/__tests__/suits/Provider.test.tsx index a4aafc0..57fe1d2 100644 --- a/__tests__/suits/Provider.test.tsx +++ b/__tests__/suits/Provider.test.tsx @@ -142,4 +142,24 @@ describe('test ValidatorProvider', () => { await tick(); expect(mockFn).toHaveBeenCalled() }); + + it('should indicate whether the area is dirty', async () => { + const provider = mount( + + {({ dirty }) => ( + <> + + + +
{dirty ? 'yes' : 'no'}
+ + )} +
+ ); + + provider.find('input').at(0).simulate('blur'); + await tick(); + expect(provider.find('div').text()).toBe('no'); + + }) }) diff --git a/src/AreaScope.ts b/src/AreaScope.ts index e48ac56..2723cf9 100644 --- a/src/AreaScope.ts +++ b/src/AreaScope.ts @@ -3,4 +3,8 @@ export interface AreaScope { * The errors after validating the area */ errors: string[]; + /** + * Flag indicating the area is dirty + */ + dirty: boolean; } diff --git a/src/ProviderScope.ts b/src/ProviderScope.ts index 287fefe..3dc081e 100644 --- a/src/ProviderScope.ts +++ b/src/ProviderScope.ts @@ -3,4 +3,8 @@ export interface ProviderScope { * Validate all areas in the provider and call callback when valid */ validate: (onValidated?: () => void) => Promise; + /** + * Flag indicating one or more areas are dirty + */ + dirty: boolean; } diff --git a/src/components/ValidatorArea.tsx b/src/components/ValidatorArea.tsx index 6f1258d..a924eb0 100644 --- a/src/components/ValidatorArea.tsx +++ b/src/components/ValidatorArea.tsx @@ -202,7 +202,8 @@ export class ValidatorArea extends React.Component; - errors: Messages + errors: Messages; + dirty: boolean; } export class ValidatorProvider extends React.Component { public readonly state: ValidatorProviderState = { areas: {}, - errors: {} + errors: {}, + dirty: false } /** @@ -45,13 +47,21 @@ export class ValidatorProvider extends React.Component void): Promise { const { areas } = this.state; - const dirtyAreas = (await Promise.all(Object.values(areas) - .map((area) => area.validate()) - )).filter((clean) => !clean); - - if (!dirtyAreas.length && onValidated) { - onValidated(); - } + this.setState({ + dirty: false + }, async (): Promise => { + const dirtyAreas = (await Promise.all(Object.values(areas) + .map((area) => area.validate()) + )).filter((clean: boolean) => !clean); + + if (!dirtyAreas.length && onValidated) { + onValidated(); + } else { + this.setState({ + dirty: true + }) + } + }); } /** @@ -59,7 +69,8 @@ export class ValidatorProvider extends React.Component void): Promise => this.validate(onValidated) + validate: (onValidated?: () => void): Promise => this.validate(onValidated), + dirty: this.state.dirty }; } From 66db57c2aa1d2929050cef5e70e6b2ba52eab62e Mon Sep 17 00:00:00 2001 From: Eran Machiels Date: Wed, 3 Feb 2021 08:23:24 +0100 Subject: [PATCH 02/10] Moved dirty to state --- src/components/ValidatorArea.tsx | 20 ++++++++------------ 1 file changed, 8 insertions(+), 12 deletions(-) diff --git a/src/components/ValidatorArea.tsx b/src/components/ValidatorArea.tsx index a924eb0..ad61605 100644 --- a/src/components/ValidatorArea.tsx +++ b/src/components/ValidatorArea.tsx @@ -18,6 +18,7 @@ export interface ValidatorAreaPropsWithDefault extends ValidatorAreaProps { interface ValidatorAreaState { errors: string[]; + dirty: boolean; } interface ValidatorAreaComponentsProps { @@ -41,16 +42,12 @@ export class ValidatorArea extends React.Component { return new Promise((resolve) => { - this.dirty = false; this.setState(() => ({ + dirty: false, errors: [] }), () => { const { @@ -94,11 +91,10 @@ export class ValidatorArea extends React.Component { - this.dirty = !passed; - if (!passed) { this.setState({ - errors: validator.getErrors() + errors: validator.getErrors(), + dirty: true }, () => { resolve(false); }) @@ -199,11 +195,11 @@ export class ValidatorArea extends React.Component Date: Wed, 3 Feb 2021 08:41:44 +0100 Subject: [PATCH 03/10] WIP pending --- __tests__/suits/Area.test.tsx | 107 +++++++++++++++++++++---------- src/AreaScope.ts | 4 ++ src/components/ValidatorArea.tsx | 31 ++++++--- 3 files changed, 99 insertions(+), 43 deletions(-) diff --git a/__tests__/suits/Area.test.tsx b/__tests__/suits/Area.test.tsx index b241374..5590b0d 100644 --- a/__tests__/suits/Area.test.tsx +++ b/__tests__/suits/Area.test.tsx @@ -17,13 +17,31 @@ describe('test ValidatorProvider', () => { return 'not passed'; } }); - Validator.extend('required', required) + Validator.extend('required', required); + + jest.useFakeTimers(); + }); + Validator.extend('long_wait', { + async passed(): Promise { + return new Promise((resolve: (value: boolean) => void): void => { + setTimeout(() => { + resolve(true); + }, 100); + }) + }, + message(): string { + return 'test'; + } + }) + + afterEach(() => { + jest.useRealTimers(); }); it('should render input', () => { const area = mount( - + ); @@ -34,7 +52,7 @@ describe('test ValidatorProvider', () => { const area = mount( {() => ( - + )} ); @@ -65,8 +83,8 @@ describe('test ValidatorProvider', () => { <> <>
- - + + <>
@@ -80,7 +98,7 @@ describe('test ValidatorProvider', () => { it('should apply rules on blur', async () => { const area = mount( - + ); @@ -92,7 +110,7 @@ describe('test ValidatorProvider', () => { it('should not apply rules on blur when non-blurrable element', () => { const area = mount( - + ); @@ -103,10 +121,10 @@ describe('test ValidatorProvider', () => { it('should render error when area dirty', async () => { const area = mount( - {({ errors }) => { + {({errors}) => { return ( <> - + {!!errors.length &&
{errors[0]}
} ); @@ -125,7 +143,7 @@ describe('test ValidatorProvider', () => { const area = mount( - + ); @@ -146,15 +164,15 @@ describe('test ValidatorProvider', () => { const provider = mount( - {({ validate }: ProviderScope) => ( + {({validate}: ProviderScope) => ( <> - + - + -