Skip to content

Commit 269034e

Browse files
fix: Refactor DatePicker component (#337)
1 parent b94cea1 commit 269034e

File tree

2 files changed

+60
-160
lines changed

2 files changed

+60
-160
lines changed

src/DatePicker/DatePicker.js

Lines changed: 32 additions & 151 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,6 @@ export class DatePicker extends Component {
3131

3232
//This is being used only when the user presses enter or clicks outside of the component
3333
formatDate = (date) => {
34-
let regex = /[!$%^&*()_+|~=`{}\[\]:'<>?,.\a-zA-Z]/;
3534
let formatDate = '';
3635
if (this.props.enableRangeSelection) {
3736
if (date.length === 0) {
@@ -61,125 +60,13 @@ export class DatePicker extends Component {
6160
secondDateDay +
6261
'/' +
6362
secondDateYear;
64-
} else {
65-
//Checks if the type of date doesn't match those types and that it doesn't contain any special character symbols
66-
if (date.toString().search(regex) !== 1) {
67-
return '';
68-
} else {
69-
let month = date[0].getMonth();
70-
let day = date[0].getDate();
71-
let year = date[0].getFullYear();
72-
73-
formatDate = month + '/' + day + '/' + year;
74-
}
7563
}
7664
return formatDate;
7765
}
7866

7967
sendUpdate = (e) => {
80-
let regex = /[!$%^&*()_+|~=`{}\[\]:'<>?,.\a-zA-Z]/;
8168
if (e.key === 'Enter') {
82-
//Checks first if range is enabled
83-
if (this.props.enableRangeSelection) {
84-
//If the formattedDate contains a list of special characters symbols then it will be reset
85-
if (
86-
this.state.formattedDate.search(regex) !== -1 ||
87-
this.state.formattedDate === '' ||
88-
this.state.formattedDate.split('-').length < 2
89-
) {
90-
this.setState({
91-
formattedDate: '',
92-
arrSelectedDates: 'undefined',
93-
hidden: false
94-
});
95-
} else {
96-
//Breaks the input into an array
97-
let dateRange = this.state.formattedDate.split('-');
98-
let dateSeparatedFirstRange = dateRange[0].split('/');
99-
let dateSeparatedSecondRange = dateRange[1].split('/');
100-
101-
//First date
102-
let firstYearRange = parseInt(dateSeparatedFirstRange[2], 10);
103-
let firstDateRange = parseInt(dateSeparatedFirstRange[1], 10);
104-
let firstMonthRange = parseInt(dateSeparatedFirstRange[0], 10);
105-
106-
//Second date
107-
let secondYearRange = parseInt(dateSeparatedSecondRange[2], 10);
108-
let secondDateRange = parseInt(dateSeparatedSecondRange[1], 10);
109-
let secondMonthRange = parseInt(dateSeparatedSecondRange[0], 10);
110-
111-
//Checks if the input is actually numbers and follows the required form
112-
if (
113-
(!isNaN(firstYearRange) ||
114-
!isNaN(firstDateRange) ||
115-
!isNaN(firstMonthRange)) &&
116-
(!isNaN(secondYearRange) ||
117-
!isNaN(secondDateRange) ||
118-
!isNaN(secondMonthRange)) &&
119-
(1 <= firstDateRange && firstDateRange <= 31) &&
120-
(1 < firstMonthRange && firstMonthRange <= 12) &&
121-
firstYearRange <= 3000 &&
122-
(1 <= secondDateRange && secondDateRange <= 31) &&
123-
(1 < secondMonthRange && secondMonthRange <= 12) &&
124-
secondYearRange <= 3000
125-
) {
126-
let firstDate = new Date(
127-
firstYearRange,
128-
firstMonthRange - 1,
129-
firstDateRange
130-
);
131-
let secondDate = new Date(
132-
secondYearRange,
133-
secondMonthRange - 1,
134-
secondDateRange
135-
);
136-
let arrSelected = [];
137-
//Swaps the order in case one date is bigger than the other
138-
firstDate.getTime() > secondDate.getTime()
139-
? (arrSelected = [secondDate, firstDate])
140-
: (arrSelected = [firstDate, secondDate]);
141-
142-
this.setState({
143-
selectedDate: '',
144-
arrSelectedDates: arrSelected
145-
});
146-
} else {
147-
this.setState({
148-
formattedDate: '',
149-
selectedDate: 'undefined',
150-
arrSelectedDates: 'undefined'
151-
});
152-
}
153-
}
154-
} else {
155-
if (this.state.formattedDate.search(regex) !== -1) {
156-
this.setState({
157-
formattedDate: this.formatDate(this.state.selectedDate),
158-
selectedDate: 'undefined'
159-
});
160-
} else {
161-
let dateSeparated = this.state.formattedDate.split('/');
162-
let year = parseInt(dateSeparated[2], 10);
163-
let date = parseInt(dateSeparated[1], 10);
164-
let month = parseInt(dateSeparated[0], 10);
165-
166-
if (
167-
(!isNaN(year) || !isNaN(date) || !isNaN(month)) &&
168-
(1 <= date && date <= 31) &&
169-
(1 < month && month <= 12) &&
170-
year <= 3000
171-
) {
172-
this.setState({
173-
selectedDate: new Date(year, month - 1, date)
174-
});
175-
} else {
176-
this.setState({
177-
selectedDate: 'undefined',
178-
formattedDate: ''
179-
});
180-
}
181-
}
182-
}
69+
this.validateDates();
18370
}
18471
}
18572

@@ -198,8 +85,9 @@ export class DatePicker extends Component {
19885
this.clickOutside();
19986
};
20087

201-
clickOutside = () => {
88+
validateDates = () => {
20289
let regex = /[!$%^&*()_+|~=`{}\[\]:'<>?,.\a-zA-Z]/;
90+
//Checks first if range is enabled
20391
if (this.props.enableRangeSelection) {
20492
//If the formattedDate contains a list of special characters symbols then it will be reset
20593
if (
@@ -210,37 +98,31 @@ export class DatePicker extends Component {
21098
this.setState({
21199
formattedDate: '',
212100
arrSelectedDates: 'undefined',
213-
hidden: true
101+
hidden: false
214102
});
215103
} else {
216-
//The range dates being split.
104+
//Breaks the input into an array
217105
let dateRange = this.state.formattedDate.split('-');
218106
let dateSeparatedFirstRange = dateRange[0].split('/');
219107
let dateSeparatedSecondRange = dateRange[1].split('/');
220108

109+
//First date
221110
let firstYearRange = parseInt(dateSeparatedFirstRange[2], 10);
222111
let firstDateRange = parseInt(dateSeparatedFirstRange[1], 10);
223112
let firstMonthRange = parseInt(dateSeparatedFirstRange[0], 10);
224113

114+
//Second date
225115
let secondYearRange = parseInt(dateSeparatedSecondRange[2], 10);
226116
let secondDateRange = parseInt(dateSeparatedSecondRange[1], 10);
227117
let secondMonthRange = parseInt(dateSeparatedSecondRange[0], 10);
228118

229-
if (
230-
(!isNaN(firstYearRange) ||
231-
!isNaN(firstDateRange) ||
232-
!isNaN(firstMonthRange)) &&
233-
(!isNaN(secondYearRange) ||
234-
!isNaN(secondDateRange) ||
235-
!isNaN(secondMonthRange)) &&
236-
(1 <= firstDateRange && firstDateRange <= 31) &&
237-
(1 < firstMonthRange && firstMonthRange <= 12) &&
119+
//Checks if the input is actually numbers and follows the required form
120+
if ((1 <= firstDateRange && firstDateRange <= 31) &&
121+
(1 <= firstMonthRange && firstMonthRange <= 12) &&
238122
firstYearRange <= 3000 &&
239123
(1 <= secondDateRange && secondDateRange <= 31) &&
240-
(1 < secondMonthRange && secondMonthRange <= 12) &&
241-
secondYearRange <= 3000 &&
242-
dateRange[0].search(regex) === -1 &&
243-
dateRange[1].search(regex) === -1
124+
(1 <= secondMonthRange && secondMonthRange <= 12) &&
125+
secondYearRange <= 3000
244126
) {
245127
let firstDate = new Date(
246128
firstYearRange,
@@ -252,26 +134,23 @@ export class DatePicker extends Component {
252134
secondMonthRange - 1,
253135
secondDateRange
254136
);
137+
let arrSelected = [];
255138
//Swaps the order in case one date is bigger than the other
256-
if (firstDate.getTime() > secondDate.getTime()) {
257-
this.setState({
258-
selectedDate: '',
259-
arrSelectedDates: [secondDate, firstDate]
260-
});
261-
} else {
262-
this.setState({
263-
selectedDate: '',
264-
arrSelectedDates: [firstDate, secondDate]
265-
});
266-
}
139+
firstDate.getTime() > secondDate.getTime()
140+
? (arrSelected = [secondDate, firstDate])
141+
: (arrSelected = [firstDate, secondDate]);
142+
143+
this.setState({
144+
selectedDate: '',
145+
arrSelectedDates: arrSelected
146+
});
267147
} else {
268148
this.setState({
269149
formattedDate: '',
270-
arrSelectedDates: 'undefined',
271-
selectedDate: ''
150+
selectedDate: 'undefined',
151+
arrSelectedDates: 'undefined'
272152
});
273153
}
274-
this.setState({ hidden: true });
275154
}
276155
} else {
277156
if (this.state.formattedDate.search(regex) !== -1) {
@@ -285,24 +164,26 @@ export class DatePicker extends Component {
285164
let date = parseInt(dateSeparated[1], 10);
286165
let month = parseInt(dateSeparated[0], 10);
287166

288-
if (
289-
(!isNaN(year) || !isNaN(date) || !isNaN(month)) &&
290-
(1 <= date && date <= 31) &&
291-
(1 < month && month <= 12) &&
167+
if ((1 <= date && date <= 31) &&
168+
(1 <= month && month <= 12) &&
292169
year <= 3000
293170
) {
294171
this.setState({
295172
selectedDate: new Date(year, month - 1, date)
296173
});
297174
} else {
298175
this.setState({
299-
formattedDate: '',
300-
selectedDate: 'undefined'
176+
selectedDate: 'undefined',
177+
formattedDate: ''
301178
});
302179
}
303180
}
304-
this.setState({ hidden: true });
305181
}
182+
}
183+
184+
clickOutside = () => {
185+
this.validateDates();
186+
this.setState({ hidden: true });
306187
};
307188

308189
updateDate = (date) => {

src/DatePicker/DatePicker.test.js

Lines changed: 28 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -202,33 +202,52 @@ describe('<DatePicker />', () => {
202202
let endRangeDate = new Date();
203203
endRangeDate.setDate(endRangeDate.getDate() + 3);
204204

205-
let arrDates = [startRangeDate, endRangeDate];
206-
wrapper.instance().updateDate(arrDates);
207-
208205
let formattedDate = `${startRangeDate.getMonth() +
209206
1}/${startRangeDate.getDate()}/${startRangeDate.getFullYear()}-${endRangeDate.getMonth() +
210207
1}/${endRangeDate.getDate()}/${endRangeDate.getFullYear()}`;
211208

209+
wrapper.find('input[type="text"]')
210+
.simulate('change', { target: { value: formattedDate } });
211+
212+
wrapper.find('input[type="text"]').simulate('keypress', { key: 'Enter' });
213+
212214
expect(wrapper.state('formattedDate')).toEqual(formattedDate);
213215
expect(wrapper.state('arrSelectedDates').length).toEqual(2);
216+
});
214217

215-
wrapper.find('input[type="text"]').simulate('keypress', { key: 'Enter' });
218+
test('pressing enter key on date input where start date > than end date', () => {
219+
wrapper = mount(rangeDatePicker);
216220

217-
// make start date bigger than end date
218-
arrDates = [endRangeDate, startRangeDate];
219-
wrapper.instance().updateDate(arrDates);
221+
let startRangeDate = new Date();
222+
let endRangeDate = new Date();
223+
endRangeDate.setDate(endRangeDate.getDate() + 3);
220224

221225
let switchFormattedDate = `${endRangeDate.getMonth() +
222226
1}/${endRangeDate.getDate()}/${endRangeDate.getFullYear()}-${startRangeDate.getMonth() +
223227
1}/${startRangeDate.getDate()}/${startRangeDate.getFullYear()}`;
224228

229+
wrapper.find('input[type="text"]')
230+
.simulate('change', { target: { value: switchFormattedDate } });
231+
232+
wrapper.find('input[type="text"]').simulate('keypress', { key: 'Enter' });
233+
225234
expect(wrapper.state('formattedDate')).toEqual(switchFormattedDate);
226235
expect(wrapper.state('arrSelectedDates').length).toEqual(2);
236+
});
227237

238+
test('enter a valid date string', () => {
239+
// enter a valid date input
240+
wrapper = mount(defaultDatePicker);
241+
let date = new Date();
242+
let formattedDate = `${date.getMonth() +
243+
1}/${date.getDate()}/${date.getFullYear()}`;
244+
wrapper.find('input[type="text"]')
245+
.simulate('change', { target: { value: formattedDate } });
246+
247+
expect(wrapper.state('formattedDate')).toEqual(formattedDate);
228248
wrapper.find('input[type="text"]').simulate('keypress', { key: 'Enter' });
229249

230-
expect(wrapper.state('formattedDate')).toBe('');
231-
expect(wrapper.state('selectedDate')).toBe('undefined');
250+
expect(wrapper.state('selectedDate')).toEqual(new Date(date.getFullYear(), date.getMonth(), date.getDate()));
232251
});
233252

234253
test('enter an invalid date string', () => {

0 commit comments

Comments
 (0)