12

I've started to work on Javascript recently. What I am testing is checking the DoB in valid format. Next step will be checking the age.

What my HTML code includes is below

<form name="ProcessInfo" action="#" method="POST" enctype="multipart/form-data" target="_self" onsubmit="return checkForm();">
.
.
.
.
<br>
<label for="txtDOB">Date of Birth:* </label>
<input id="txtDOB" type="text" name="txtDOB" size="12">
format: ##/##/####
<br>
.
.
.
</form>
.
.

and I did the following in my .js file

var errMessage = "";

function checkForm() {
    validateName();
    validateSurname();
    carSelect();
    validateDOB();

    if (errMessage == "") {
    } else {
        alert(errMessage);
    }
}

...

function validateDOB()
{
    var dob = document.forms["ProcessInfo"]["txtDOB"].value;
    var pattern = /^([0-9]{2})-([0-9]{2})-([0-9]{4})$/;
    if (dob == null || dob == "" || !pattern.test(dob)) {
        errMessage += "Invalid date of birth\n";
        return false;
    }
    else {
        return true
    }
}

I tried to check if its valid with regular expression but I always get an alert even if I type the date correctly. And how can I seperate the DD / MM / YYYY to calculate the age?

shabeer90
  • 5,161
  • 4
  • 47
  • 65
A. Mesut Konuklar
  • 611
  • 3
  • 12
  • 29
  • Your pattern separates by dashes (`-`), not slashes (`/`). Which one do you actually want? Also, you can use `\d` as an equivalent for `[0-9]`. – Ingo Bürk Nov 06 '13 at 18:52
  • Thanks for the warning! I wanted to use `/` and thought I was using it with doing `/^` when I change `-` to `/` I get an error. – A. Mesut Konuklar Nov 06 '13 at 18:55
  • Is 99/99/9999 a valid date? – BalusC Nov 06 '13 at 18:58
  • @BalusC There is no reason to put a lot of effort into disallowing `99/99/9999`. If a user wants to lie, he can still enter a valid but incorrect date. Validation like this should only be for feedback purposes in case of typos. – Ingo Bürk Nov 06 '13 at 19:00
  • 1
    @Ingo: just wanted to give some food for thought ;) By the way, `\d` should be used carefully in other languges than JS, such as Java/C#. It namely also matches non-Latin numerals such as Hebrew, Chinese, Persian, etc. – BalusC Nov 06 '13 at 19:02
  • Fair enough. :) @user1700286 Please also remember that client-side validation is useless if it's for more than a simple user feedback. If, f.ex., you want to only allow 18+ people to use the service, you *need* to to the validation server-side (besides the fact that they can just lie, of course). – Ingo Bürk Nov 06 '13 at 19:04

16 Answers16

24

If you want to use forward slashes in the format, the you need to escape with back slashes in the regex:

var pattern =/^([0-9]{2})\/([0-9]{2})\/([0-9]{4})$/;

http://jsfiddle.net/P9TER/

Drahcir
  • 11,772
  • 24
  • 86
  • 128
14

I suggest using moment.js which provides an easy to use method for doing this.

interactive demo

function validate(date){
    var eighteenYearsAgo = moment().subtract(18, "years");
    var birthday = moment(date);

    if (!birthday.isValid()) {
        return "invalid date";    
    }
    else if (eighteenYearsAgo.isAfter(birthday)) {
        return "okay, you're good";    
    }
    else {
        return "sorry, no";    
    }
}

To include moment in your page, you can use CDNJS:

<script src="//cdnjs.cloudflare.com/ajax/libs/moment.js/2.4.0/moment.min.js"></script>
Brigand
  • 84,529
  • 20
  • 165
  • 173
8

I'd utilize the built in Date object to do the validation for me. Even after you switch from - to / you still need to check whether the month is between 0 and 12, the date is between 0 and 31 and the year between 1900 and 2013 for example.

function validateDOB(){

    var dob = document.forms["ProcessInfo"]["txtDOB"].value;
    var data = dob.split("/");
    // using ISO 8601 Date String
    if (isNaN(Date.parse(data[2] + "-" + data[1] + "-" + data[0]))) {
        return false;
    }

    return true;
}

See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/parse#Example:_Using_parse for more information.

Nylon Smile
  • 8,990
  • 1
  • 25
  • 34
Lim H.
  • 9,870
  • 9
  • 48
  • 74
5

If you want to use forward slashes in the format, the you need to escape with back slashes in the regex:

   
var dateformat = /^(0?[1-9]|1[012])[\/\-](0?[1-9]|[12][0-9]|3[01])[\/\-]\d{4}$/;
user1089766
  • 597
  • 6
  • 14
4
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title></title>
<script>
    function dateCheck() {
        debugger;

        var inputValues = document.getElementById('dateInput').value + ' ' + document.getElementById('monthInput').value + ' ' + document.getElementById('yearInput').value;

        var d = new Date();
        var n = d.getHours();
        var m = d.getMinutes();
        var p = d.getSeconds();

        var date = document.getElementById("dateInput").value;
        var month = document.getElementById("monthInput").value;
        var year = document.getElementById("yearInput").value;

        var dateCheck = /^(0?[1-9]|[12][0-9]|3[01])$/;
        var monthCheck = /^(0[1-9]|1[0-2])$/;
        var yearCheck = /^\d{4}$/; 

        if (month.match(monthCheck) && date.match(dateCheck) && year.match(yearCheck)) {

            var ListofDays = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];

            if (month == 1 || month > 2) {
                if (date > ListofDays[month - 1]) {
                    alert('Invalid date format!');
                    return false;
                }
            }

            if (month == 2) {
                var leapYear = false;
                if ((!(year % 4) && year % 100) || !(year % 400)) {
                    leapYear = true;
                }

                if ((leapYear == false) && (date >= 29)) {
                    alert('Invalid date format!');
                    return false;
                }

                if ((leapYear == true) && (date > 29)) {
                    alert('Invalid date format!');
                    return false;
                }

            }
            var flag = 1
        }

        else {
            alert("invalid date");


        }
        if (flag == 1) {
            alert("the date is:" + inputValues + " " + "The time is:" + n + ":" + m + ":" + p);
        }

        clear();
    }

    function clear() {
        document.myForm.dateInput.value = "";
        document.myForm.monthInput.value = "";
        document.myForm.yearInput.value = "";
    }


</script>

</head>


<body>  
    <div>  
        <form name="myForm" action="#">   
            <table>
                <tr>
                    <td>Enter Date</td>
                    <td><input type='text' name='dateInput' id="dateInput" placeholder="Date"  maxlength="2" onclick="dateCheck(document.myForm.dateInput)" onkeypress="return event.charCode === 0 || /\d/.test(String.fromCharCode(event.charCode));"/></td>
                    <td><span id="span1"></span></td>
                </tr>
                <tr>
                    <td>Enter Month</td>
                    <td><input type='text' name='monthInput' id="monthInput" placeholder="Month"  maxlength="2" onclick="dateCheck(document.myForm.dateInput)" onkeypress="return event.charCode === 0 || /\d/.test(String.fromCharCode(event.charCode));"/></td>
                    <td><span id="span2"></span></td>
                </tr>
                <tr>
                    <td>Enter Year</td>
                    <td><input type='text' name='yearInput' id="yearInput" placeholder="Year" minlength="4" maxlength="4" onclick="dateCheck()" onkeypress="return event.charCode === 0 || /\d/.test(String.fromCharCode(event.charCode));"/></td>
                    <td><span id="span3"></span></td>
                </tr>

                <tr>
                    <td></td>
                    <td><input type="submit" name="submit" value="Submit" onclick="dateCheck()"/></td>
                </tr>
            </table>
        </form>  
    </div>   
</body>  
</html>
<td>
Mayur Narula
  • 150
  • 1
  • 4
2

Using pattern and check validate:

var input = '33/15/2000';

var pattern = /^((0[1-9]|[12][0-9]|3[01])(\/)(0[13578]|1[02]))|((0[1-9]|[12][0-9])(\/)(02))|((0[1-9]|[12][0-9]|3[0])(\/)(0[469]|11))(\/)\d{4}$/;

alert(pattern.test(input));
NobodyNada
  • 7,529
  • 6
  • 44
  • 51
rung
  • 69
  • 1
  • 1
1

You have used regular expression for this format : DD - MM- YYYY

If you need this format DD/MM/YYYY use

var pattern =/^([0-9]{2})\/([0-9]{2})\/([0-9]{4})$/;
abhiklpm
  • 1,603
  • 2
  • 16
  • 21
1

It is two problems - is the slashes the right places and is it a valid date. I would suggest you catch input changes and put the slashes in yourself. (annoying for the user)

The interesting problem is whether they put in a valid date and I would suggest exploiting how flexible js is:

function isValidDate(str) {
  var newdate = new Date();
  var yyyy = 2000 + Number(str.substr(4, 2));
  var mm = Number(str.substr(2, 2)) - 1;
  var dd = Number(str.substr(0, 2));
  newdate.setFullYear(yyyy);
  newdate.setMonth(mm);
  newdate.setDate(dd);
  return dd == newdate.getDate() && mm == newdate.getMonth() && yyyy == newdate.getFullYear();
}
console.log(isValidDate('jk'));//false
console.log(isValidDate('290215'));//false
console.log(isValidDate('290216'));//true
console.log(isValidDate('292216'));//false
Rune Jeppesen
  • 1,121
  • 13
  • 22
  • Can define `var newdate = new Date(yyyy, mm, dd);` last in one line instead of four. – Y.B. Dec 01 '17 at 11:01
0

To get the values use pattern.exec() instead of pattern.test() (the .test() returns a boolean value).

drk
  • 21
  • 6
0
         if(!/^(0?[1-9]|[12][0-9]|3[01])[\/\-](0?[1-9]|1[012])[\/\-]\d{2}$/.test($(this).val())){
                     alert('Date format incorrect (DD/MM/YY)');
                     $(this).datepicker('setDate', "");
                     return false;
                }

This code will validate date format DD/MM/YY

Sri
  • 496
  • 1
  • 5
  • 20
  • The problem with using Regular expression is it is difficult to identify exactly what made the date invalid. It either gives a True or a false-Without any reason which will help the user to fix. We have to write multiple regular expressions to sort this problem. – Ananda Apr 22 '16 at 13:22
0

with leading zero for day and month

var pattern =/^(0[1-9]|1[0-9]|2[0-9]|3[0-1])\/(0[1-9]|1[0-2])\/([0-9]{4})$/;

and with both leading zero/without leading zero for day and month

var pattern =/^(0?[1-9]|1[0-9]|2[0-9]|3[0-1])\/(0?[1-9]|1[0-2])\/([0-9]{4})$/;
Misho
  • 2,911
  • 2
  • 14
  • 9
0

I use the code I found @.w3resources

The code takes care of

  • month being less than 12,

  • days being less than 32

  • even works with leap years. While Using in my project for leap year I modify the code like

    if ((lyear==false) && (dd>=29))
    {
    alert('Invalid date format!');
    return false;
    }

    if ((lyear==false) && (dd>=29))
    {
    alert('not a Leap year February cannot have more than 28days');
    return false;
    }

Rather than throwing the generic "Invalid date format" error which does not make much sense to the user. I modify the rest of the code to provide valid error message like month cannot be more than 12, days cannot be more than 31 etc.,

The problem with using Regular expression is it is difficult to identify exactly what went wrong. It either gives a True or a false-Without any reason why it failed. We have to write multiple regular expressions to sort this problem.

Community
  • 1
  • 1
Ananda
  • 888
  • 9
  • 19
0
var date=/^[0-9]{1,2}\-[0-9]{1,2}\-[0-9]{1,4}$/;

if(!date.test(form.date.value))

alert("Enter correct date");

else
alert(" working");
Petter Friberg
  • 21,252
  • 9
  • 60
  • 109
  • No. Seriously. Please give some context and explanation for the code. [How to answer](http://stackoverflow.com/help/how-to-answer) – AgataB Sep 22 '16 at 20:57
0

You can use attributes of html tag instead of validation from html input type ="date" can be used instead of validating it. That's the benifits html 5 gives you

0

If you're using moment then that's the single line code:

moment(date).format("DD/MM/YYYY").isValid()

Kuldeep Saxena
  • 1,803
  • 1
  • 14
  • 17
0

When we put only pattern it's not simple to check every possible date combination. Users can enter valid numbers like 99/99/9999 but it's not a valid date. Even If we limit days and months to a more restrictive value (30/31 days and 0-12 months) we still may get a case where we have leap year, febraury etc. and we cannot properly validate them using regex. So the better approach is to use a date object itself.

let InputDate = "99/99/9999"
let pattern =/^([0-9]{2})\/([0-9]{2})\/([0-9]{4})$/;
let editDate = InputDate.replace("\/","-")

let dateValidation = function validation(){
  
if(pattern.test(InputDate) && new Date(editDate) == 'Invalid Date'){
  return false;
}else{
  return true;
}

}

console.log(dateValidation()) //Return false
AkkiJS
  • 1
  • 3