-1

I am creating a date validation in Javascript with regex. In some cases it is not working

'(?:(0[1-9]|1[012])[\/.](0[1-9]|[12][0-9]|3[01])[\/.][0-9]{4})'

11/11/1000 - Correct

11/11/0000 - INVALID

Zero should not be allowed in year

InSync
  • 4,851
  • 4
  • 8
  • 30
user5798214
  • 529
  • 1
  • 6
  • 20
  • Does this answer your question? [Regex to validate date formats dd/mm/YYYY, dd-mm-YYYY, dd.mm.YYYY, dd mmm YYYY, dd-mmm-YYYY, dd/mmm/YYYY, dd.mmm.YYYY with Leap Year Support](https://stackoverflow.com/questions/15491894/regex-to-validate-date-formats-dd-mm-yyyy-dd-mm-yyyy-dd-mm-yyyy-dd-mmm-yyyy) – InSync May 30 '23 at 13:04
  • so you need to change the last part `[0-9]{4}` and I am betting it does not really account for leap years and months with 28/30/31.... – epascarello May 30 '23 at 13:07
  • @InSync the regex in the accepted solution doesn't match either of the OP's supplied examples – evolutionxbox May 30 '23 at 13:07
  • 4
    In general, validating dates with regex is mostly a terrible idea. Use a library, or the soon-to-be-accepted [Temporal](https://tc39.es/proposal-temporal/docs/). – InSync May 30 '23 at 13:07
  • 1
    @evolutionxbox I can't find a better duplicate target. Also, that's not the point. – InSync May 30 '23 at 13:12
  • Convert the string to a `Date` and check the year. [Here](https://stackblitz.com/edit/js-hgfmem?file=index.js) is a function to convert a string to `Date`. – KooiInc May 30 '23 at 13:45

2 Answers2

1

try using this regex instead using a negative look ahead on the 0000

^(?:(0[1-9]|1[012])[\/.](0[1-9]|[12][0-9]|3[01])[\/.](?!0{4})\d{4})$
mplungjan
  • 169,008
  • 28
  • 173
  • 236
Yazdan Qm
  • 21
  • 4
1

You should avoid using a regular expression to validate dates. Parse the date string as an actual date and check to see if it is actually valid.

Note: The usage of +token[n] and parseInt(token[n], 10) below are interchangeable.

const validateDate = (dateString) => {
  const tokens = dateString.split('/');
  // Must be 3 tokens
  if (tokens.length !== 3) return false;
  // Must all be numeric
  if (tokens.some(token => isNaN(parseInt(token, 10)))) return false;
  // Year must !== 0
  if (+tokens[2] === 0) return false;
  const date = new Date(+tokens[2], +tokens[0] - 1, +tokens[1]);
  // Must be a valid date
  return date instanceof Date && !isNaN(date);
};

console.log(validateDate('11/11/1000')); // true
console.log(validateDate('11/11/0000')); // false

Here is an alternate version that is slightly optimized.

const validateDate = (dateString) => {
  const [month, date, year] = dateString.split('/').map(token => +token);
  if (year === 0 || isNaN(year) || isNaN(month) || isNaN(date)) return false;
  const dateObj = new Date(year, month - 1, date);
  return dateObj instanceof Date && !isNaN(dateObj);
};

console.log(validateDate('11/11/1000')); // true
console.log(validateDate('11/11/0000')); // false
Mr. Polywhirl
  • 42,981
  • 12
  • 84
  • 132