React-day-picker: React dayPickerInput formatting to MM/DD/YYYY prevents entering the date in the input text box

Created on 7 Dec 2017  路  11Comments  路  Source: gpbl/react-day-picker

I have the following code sand box which is a fork of the range with 2 inputs example., https://codesandbox.io/s/w6vnlox29l I have it working the way I want but I want to input dates as MM/DD/YYYY instead of the default format. When I add the following attributes:

      <DayPickerInput
            value={from}
            format="M/D/YYYY"
            formatDate={formatDate}
            parseDate={parseDate} 
            placeholder="MM/DD/YYYY"
            onDayChange={this.handleFromChange}
            dayPickerProps={{
              selectedDays: [from, { from, to }],
              modifiers,
              disabledDays: {
                after: new Date(),
              },
              numberOfMonths: 2,
              toMonth: new Date(),
            }}
          />

I can no longer correctly enter the date in the input field the date. When I remove the format, formatDate and parseDate attributes the date picker input functions the way I expected. I have read the documentation but think I may be missing something simple. How can I use the input text box and date picker with dates formatted as MM/DD/YYYY?

good first issue

Most helpful comment

I've noticed that the formatDate provided is using moment in "forgiving mode" (https://momentjs.com/guides/#/parsing/forgiving-mode/). Every time the input changes, the value is parsed and moment tries its best to make a valid date out of it, overriding the input value:

Say we have 10/10/2012 and the format is DD/MM/YYYY. If I delete the last digit of the year, the input value would be 10/10/201. Moment parses the string and, thinking the year is 201 , it tries to create a date DD/MM/YYYY by formatting the year 201 with 4 digits: 0201. The entire value is parsed as 10/10/0201 and displayed in the input.

In strict mode, moment would return undefined as the string 10/10/201 does not match DD/MM/YYYY.

A solution to fix the problem could be to set up moment to run on strict mode, but it would be hard to distinguish between empty values in the input and errors (wrong format).

I can add a pull request with this fix if you think this is the way to go.

All 11 comments

I am not 100% sure this is the same bug, but I have this reproducable example: https://codesandbox.io/s/23lvr5861r
When you focus the input field and press backspace somewhere, for example, after the "2017" part, you'll see that "2017" is changed to "0201". This bug was introduced in 7.0.0; in 6.2.1 this worked like expected.

@SpaceK33z yes same bug, thanks for reporting your example!

I've noticed that the formatDate provided is using moment in "forgiving mode" (https://momentjs.com/guides/#/parsing/forgiving-mode/). Every time the input changes, the value is parsed and moment tries its best to make a valid date out of it, overriding the input value:

Say we have 10/10/2012 and the format is DD/MM/YYYY. If I delete the last digit of the year, the input value would be 10/10/201. Moment parses the string and, thinking the year is 201 , it tries to create a date DD/MM/YYYY by formatting the year 201 with 4 digits: 0201. The entire value is parsed as 10/10/0201 and displayed in the input.

In strict mode, moment would return undefined as the string 10/10/201 does not match DD/MM/YYYY.

A solution to fix the problem could be to set up moment to run on strict mode, but it would be hard to distinguish between empty values in the input and errors (wrong format).

I can add a pull request with this fix if you think this is the way to go.

Addition to previous comment.

In docs http://react-day-picker.js.org/api/DayPickerInput/#onDayChange we have:
"Handler function called when the user types a valid day (according to the format prop) or when a day is clicked on the calendar. If the day is not valid, day and modifiers arguments will be undefined (useful to display validation warnings)."

But with Forgiving Mode, all values are valid.

This issue really does make using the day picker with a non YYYY-MM-DD very problematic for end users -- if there is anything I can do to help speed getting this PR approved, I'm more than willing to help!

@mc-funk I鈥檒l have some free time in the next days, expect release including the fix soon. Thanks for your patience!

Fix published as v7.0.6: https://codesandbox.io/s/03mxznn2rl

@gpbl should onDayChange be passed a moment instance if using the new formatDate/parseDate method? In v6, this function was receiving a moment instance

True, maybe i forgot to add it to the release notes 馃槻

It works with plain Date objects now

Thank You!

Was this page helpful?
0 / 5 - 0 ratings