14

I am doing validation for Driver's Date of birth, it should be minimum of 18 from the current date.

var Dates = $get('<%=ui_txtDOB.ClientID %>');   
var Split = Dates.value.split("/");

if (parseInt(Split[2]) > 1993) 
{
    alert("DOB year should be less than 1993");
    Dates.focus();
    return false;
}  

I am using this above JavaScript validation for checking a person's DOB above 18, but it is not correct. I need to check with today's date and it should be above 18. How can I compare and check with the current date?

Justin
  • 84,773
  • 49
  • 224
  • 367
Lakshmitha
  • 675
  • 3
  • 11
  • 17
  • 1
    It's not correct, indeed, and interestingly it will get even less correct every year to come. – Ingo Aug 17 '11 at 11:05

9 Answers9

16

I think a better alternative would be to calculate the age of the user, and use that in your if statement.

See this SO answer on how to do just that:

Calculate age in JavaScript

Community
  • 1
  • 1
Curtis
  • 101,612
  • 66
  • 270
  • 352
13

Try this.

var enteredValue = $get('<%=ui_txtDOB.ClientID %>');;
var enteredAge = getAge(enteredValue.value);
if( enteredAge > 18 ) {
    alert("DOB not valid");
    enteredValue.focus();
    return false;
}

Using this function.

function getAge(DOB) {
    var today = new Date();
    var birthDate = new Date(DOB);
    var age = today.getFullYear() - birthDate.getFullYear();
    var m = today.getMonth() - birthDate.getMonth();
    if (m < 0 || (m === 0 && today.getDate() < birthDate.getDate())) {
        age--;
    }    
    return age;
}

Demo here: http://jsfiddle.net/codeandcloud/n33RJ/

naveen
  • 53,448
  • 46
  • 161
  • 251
3

My approach is to find the date 18 (or any number) years ago from today, then see if that's after (greater) than their dob. By setting all values to date objects it makes the comparison easy.

function is_of_age(dob, age) {
  // dates are all converted to date objects
  var my_dob = new Date(dob);
  var today = new Date();
  var max_dob = new Date(today.getFullYear() - age, today.getMonth(), today.getDate());
  return max_dob.getTime() > my_dob.getTime();
}

Because the Date object can parse strings in a variety of formats, You don't have to worry too much about where dob is coming from. Simply call is_of_age("1980/12/4", 18); or is_of_age("2005-04-17", 13); or basically any string format or numeric that can be parsed as a Date parameter.

2
<script>


    function dobValidate(birth) {


        var today = new Date();
        var nowyear = today.getFullYear();
        var nowmonth = today.getMonth();
        var nowday = today.getDate();
        var b = document.getElementById('<%=TextBox2.ClientID%>').value;



        var birth = new Date(b);

        var birthyear = birth.getFullYear();
        var birthmonth = birth.getMonth();
        var birthday = birth.getDate();

        var age = nowyear - birthyear;
        var age_month = nowmonth - birthmonth;
        var age_day = nowday - birthday;


        if (age > 100) {
            alert("Age cannot be more than 100 Years.Please enter correct age")
            return false;
        }
        if (age_month < 0 || (age_month == 0 && age_day < 0)) {
            age = parseInt(age) - 1;


        }
        if ((age == 18 && age_month <= 0 && age_day <= 0) || age < 18) {
            alert("Age should be more than 18 years.Please enter a valid Date of Birth");
            return false;
        }
    }



</script>
sdsf
  • 21
  • 1
2

After looking at various methods of doing this, I decided the simplest way was to encode the dates as 8-digit integers. You can then subtract today's code from the DOB code and check if it's greater than or equal to 180000.

function isOverEighteen(year, month, day) {
  var now = parseInt(new Date().toISOString().slice(0, 10).replace(/-/g, ''));
  var dob = year * 10000 + month * 100 + day * 1; // Coerces strings to integers

  return now - dob > 180000;
}
kano
  • 5,626
  • 3
  • 33
  • 48
bat020
  • 31
  • 4
2
let TODAY = new Date(Date.now());
let EIGHTEEN_YEARS_BACK = new Date(new Date(TODAY).getDate() + "/" + new Date(TODAY).getMonth() + "/" + (new Date(TODAY).getFullYear() - 18));
let USER_INPUT = new Date("2003/12/13");
// Validate Now
let result = EIGHTEEN_YEARS_BACK > USER_INPUT // true if over 18, false if less than 18

I think this is the closest possible way to check.

Avtar Nanrey
  • 133
  • 3
  • 9
0

My favourite approach is this one:

var dateOfBirth = new Date("02/23/1900");
// calculate difference between now and the dateOfBirth (in milliseconds)
var differenceMs = Date.now() - dateOfBirth.getTime();
// convert the calculated difference in date format
var dateFromEpoch = new Date(differenceMs); 
// extract year from dateFromEpoch
var yearFromEpoch = dateFromEpoch.getUTCFullYear();
// calculate the age of the user
var age = Math.abs(yearFromEpoch - 1970);

console.log("Age of the user: " + age + " years")
Detheuss
  • 21
  • 4
  • Your answer could be improved with additional supporting information. Please [edit] to add further details, such as citations or documentation, so that others can confirm that your answer is correct. You can find more information on how to write good answers [in the help center](/help/how-to-answer). – Community Feb 23 '22 at 11:49
0

You can use the below:

var birthDate = new Date("2018-06-21");
var birthDate1 = new Date("1975-06-21");
 function underAgeValidate(birthday) {
    const diff = Date.now() - birthday.getTime();
    const ageDate = new Date(diff);
    let age = Math.abs(ageDate.getUTCFullYear() - 1970);
      return age < 18;
  };

console.log(underAgeValidate(birthDate));
console.log(underAgeValidate(birthDate1));
0

Couldn't find any simple solution that actually works as it should and it's not some kind of overkill (in other words have high "cognitive complexity"), also calculating age instead (as it is in accepted answer) wasn't an option in my case.

Figured out something like this:

const exactlyNYearsAgoDate = (yearsAgo) => new Date(
  new Date().setFullYear(new Date().getFullYear() - yearsAgo)
)

console.log(exactlyNYearsAgoDate(18))

Why do I use new Date() 3 times?

  1. new Date().getFullYear() - yearsAgo - returns only year (e.g. 2005), which my lead to pass yearsAgo - 1 also (e.g. 17yo might be valid by year, even if they didn't have birthday in this year yet).
  2. new Date().setFullYear(...) - this will basically change year of the current date, but return of this operation will be in milliseconds.
  3. (optional) new Date(...) - will parse milliseconds into Date object, which will result date exactly n years ago (n is our yearsAgo).

Validation using plain JS:

const exactlyNYearsAgoDate = (yearsAgo) => new Date(
  new Date().setFullYear(new Date().getFullYear() - yearsAgo)
)
const mockBirthday = new Date('2000-07-15T00:01:09.420Z')
const isAdult = exactlyNYearsAgoDate(18).getTime() < new Date().getTime()

console.log('isAdult:', isAdult)

Validation using Zod (docs):

z.date().max(exactlyNYearsAgoDate(18), {message: 'You are not 18 years old'})
ulou
  • 5,542
  • 5
  • 37
  • 47