whyAto8
whyAto8

Reputation: 1670

Date format regex to match date separator

I am using below code to validate the date format in dd/mm/yyyy and dd.mm.yyyy format.

function validateDate(date){
    var matches, d, m, y, cDate, format, dateFormatObj;
    dateFormatObj = { format: /^(\d{2})[./](\d{2})[./](\d{4})$/, monthPos: 2, datePos:1,    yearPos:3}

    format = dateFormatObj.format;
    matches = format.exec(date);

    d = matches[dateFormatObj.datePos];
    m = matches[dateFormatObj.monthPos] - 1;
    y = matches[dateFormatObj.yearPos];
    cDate = new Date(y, m, d);

    return cDate.getDate() == d && cDate.getMonth() == m && cDate.getFullYear() == y;
}

alert(validateDate('22/05/2017'))

This works fine for me, to validate basic date.

What i was trying to fix is that if the separator (/ or .) between the month, date and year values are different, then it should invalidate that.

What i tried was to change the regex format as /^(\d{2})[./](\d{2})\1(\d{4})$/, basically to use the same captured group as specified, but this doesn't seem to work, the "matches" comes out to be null. I have read couple of posts, but something seems to be missing. What can i do to make this work.

JS Fiddle - https://jsfiddle.net/90dstrx5/

Upvotes: 0

Views: 1459

Answers (2)

Salman Arshad
Salman Arshad

Reputation: 272096

You can rewrite the regex as follows:

/^(\d{2})([./])(\d{2})\2(\d{4})$/
//       ^            ^
//       |            +---- match capturing group #2
//       +----------------- capturing group #2

Note that the "numbers" will now be available at 1st, 3rd and 4th position in the result; separator will be at 2nd position. To eliminate any confusion use Array.splice() to eliminate it:

function validateDate(date) {
  var matches, d, m, y, cDate, format, dateFormatObj;
  dateFormatObj = {
    format: /^(\d{2})([./])(\d{2})\2(\d{4})$/,
    monthPos: 2,
    datePos: 1,
    yearPos: 3
  };
  format = dateFormatObj.format;
  matches = format.exec(date);
  if (matches === null) {
    return false;
  }
  matches.splice(2, 1);
  d = matches[dateFormatObj.datePos];
  m = matches[dateFormatObj.monthPos] - 1;
  y = matches[dateFormatObj.yearPos];
  cDate = new Date(y, m, d);
  return cDate.getDate() == d && cDate.getMonth() == m && cDate.getFullYear() == y;
}
console.log(validateDate('22/05/2017')); // true
console.log(validateDate('22/05.2017')); // false

Upvotes: 3

Pugazh
Pugazh

Reputation: 9561

I couldn't think of a way to tweak the regex. But here is an workaround with both separator specified.

function validateDate(date) {
  var matches, d, m, y, cDate, format, dateFormatObj;
  dateFormatObj = {
    format1: /^(\d{2})[.](\d{2})[.](\d{4})$/,
    format2: /^(\d{2})[/](\d{2})[/](\d{4})$/,
    monthPos: 2,
    datePos: 1,
    yearPos: 3
  }
  format1 = dateFormatObj.format1;
  format2 = dateFormatObj.format2;
  matches = format1.exec(date) || format2.exec(date);

  if (matches == null)
    return false;

  d = matches[dateFormatObj.datePos];
  m = matches[dateFormatObj.monthPos] - 1;
  y = matches[dateFormatObj.yearPos];
  cDate = new Date(y, m, d);
  return cDate.getDate() == d && cDate.getMonth() == m && cDate.getFullYear() == y;
}

alert(validateDate('22/05.2017'))

Upvotes: 1

Related Questions