218

i am trying to convert a string in the format dd-mm-yyyy into a date object in JavaScript using the following:

 var from = $("#datepicker").val();
 var to = $("#datepickertwo").val();
 var f = new Date(from);
 var t = new Date(to);

("#datepicker").val() contains a date in the format dd-mm-yyyy. When I do the following, I get "Invalid Date":

alert(f);

Is this because of the '-' symbol? How can I overcome this?

Scimonster
  • 32,893
  • 9
  • 77
  • 89
user559142
  • 12,279
  • 49
  • 116
  • 179

15 Answers15

360

Split on "-"

Parse the string into the parts you need:

var from = $("#datepicker").val().split("-")
var f = new Date(from[2], from[1] - 1, from[0])

Use regex

var date = new Date("15-05-2018".replace( /(\d{2})-(\d{2})-(\d{4})/, "$2/$1/$3"))

Why not use regex?

Because you know you'll be working on a string made up of three parts, separated by hyphens.

However, if you were looking for that same string within another string, regex would be the way to go.

Reuse

Because you're doing this more than once in your sample code, and maybe elsewhere in your code base, wrap it up in a function:

function toDate(dateStr) {
  var parts = dateStr.split("-")
  return new Date(parts[2], parts[1] - 1, parts[0])
}

Using as:

var from = $("#datepicker").val()
var to = $("#datepickertwo").val()
var f = toDate(from)
var t = toDate(to)

Or if you don't mind jQuery in your function:

function toDate(selector) {
  var from = $(selector).val().split("-")
  return new Date(from[2], from[1] - 1, from[0])
}

Using as:

var f = toDate("#datepicker")
var t = toDate("#datepickertwo")

Modern JavaScript

If you're able to use more modern JS, array destructuring is a nice touch also:

const toDate = (dateStr) => {
  const [day, month, year] = dateStr.split("-")
  return new Date(year, month - 1, day)
}
Adrian Lynch
  • 8,237
  • 2
  • 32
  • 40
  • 10
    beat me to it...but I still use DateJs. This isn't exactly correct due to a fence post error. the month is 0-11 so you need to subtract 1. f = new Date(from[2], from[1]-1, from[0]); – kasdega Aug 22 '11 at 18:27
  • 14
    Selected answer with a bug that produces wrong dates. Awesome! – epascarello Aug 22 '11 at 19:49
  • 3
    Cheers @kasdega - Edited it... a while ago! – Adrian Lynch Jan 02 '15 at 15:21
  • @AdrianLynch How to convert "Month dd, yyyy" into "MM/dd/yyyy" in javascript? – dilipkumar1007 May 12 '16 at 09:24
  • @AdrianLynch I've date in “Month dd, yyyy” formate only. Now, I've to convert it into “MM/dd/yyyy". Please suggest me. – dilipkumar1007 May 12 '16 at 09:47
  • Doesn't it need to convert day, month and year to integer ? – Malinda May 30 '17 at 03:38
  • Another example: `var date = new Date("11/04/1978".replace( /(\d{2})\/(\d{2})\/(\d{4})/, "$2/$1/$3"));`. NOTE: Using JavaScript Short Dates. Short dates are written with an "MM/DD/YYYY" syntax ( https://www.w3schools.com/js/js_date_formats.asp ). – Eduardo Lucio Oct 10 '18 at 22:59
  • When I use Modern Javascript: `toDate(dateStr)` throws an error `Uncaught TypeError: toDate is not a function`. After I change the name to `toDateTest(dateStr)` it works fine. Any ideas @AdrianLynch? – vixero Mar 06 '19 at 08:16
  • A good answer except for the "use regex" example. `new Date("05-15-2018")` produces an invalid date in Safari and Firefox at least. Suggesting converting one unsupported format to another unsupported format for parsing by the built–in parser is fraught (as demonstrated). :-) – RobG Jul 07 '22 at 13:47
139

regular expression example:

new Date( "13-01-2011".replace( /(\d{2})-(\d{2})-(\d{4})/, "$2/$1/$3") );
epascarello
  • 204,599
  • 20
  • 195
  • 236
  • 8
    A revision that also takes `/` is delimiter and a year made of 2 digits (or any count bigger than 1): `replace( /(\d{2})[-/](\d{2})[-/](\d+)/, "$2/$1/$3")` – Izhaki Dec 22 '14 at 17:32
  • 1
    Why should this be the selected answer @AdemirNuno? Why use RegEx for a string in a known format? You're not looking for a pattern, you know the first number is the day, the second the month and the third the year. RegEx is the wrong tool for the job in this case. – Adrian Lynch Jan 02 '15 at 15:24
  • A revision that takes non-digit delimiters, dates without leading zeroes and 2 or 4 digit years: `new Date( "23. 2. 15".replace( /(\d+)[^d]+(\d+)[^d]+(\d+)/, "$2/$1/$3") );` http://en.wikipedia.org/wiki/Date_format_by_country – PaulH Feb 23 '15 at 08:32
  • it's so practice guy, thanks. my date format it comes with time, so i recode it as : 'new Date( "13-01-2011".replace( /(\d{2})-(\d{2})-(\w)/, "$2/$1/$3") );' is it right? – Kamuran Sönecek Sep 29 '15 at 06:00
  • @NeerajSingh How to convert "Month dd, yyyy" into "MM/dd/yyyy" in javascript? – dilipkumar1007 May 12 '16 at 09:23
  • @dilipkumar1007: Please find your answer demo: https://jsfiddle.net/neerajsinghsonu/qhxgbuer/ – Nono May 12 '16 at 12:33
  • A revision that also takes / is separator and a year made of 2 digits `replace(/(\d{2})[-,/](\d{2})[-,/](\d+)/, "$2/$1/$3")` – MK4 Jun 07 '16 at 10:01
17

Another possibility:

var from = "10-11-2011"; 
var numbers = from.match(/\d+/g); 
var date = new Date(numbers[2], numbers[0]-1, numbers[1]);

Match the digits and reorder them

Joe
  • 80,724
  • 18
  • 127
  • 145
11

Using moment.js example:

var from = '11-04-2017' // OR $("#datepicker").val();
var milliseconds = moment(from, "DD-MM-YYYY").format('x');
var f = new Date(milliseconds)
Makah
  • 4,435
  • 3
  • 47
  • 68
9

Use this format: myDate = new Date('2011-01-03'); // Mon Jan 03 2011 00:00:00

Diodeus - James MacFarlane
  • 112,730
  • 33
  • 157
  • 176
6
var from = $("#datepicker").val(); 
var f = $.datepicker.parseDate("d-m-Y", from);
Saad Imran.
  • 4,480
  • 2
  • 23
  • 33
4

The accepted answer kinda has a bug

var from = $("#datepicker").val().split("-")
var f = new Date(from[2], from[1] - 1, from[0])

Consider if the datepicker contains "77-78-7980" which is obviously not a valid date. This would result in:

var f = new Date(7980, 77, 77);
=> Date 7986-08-15T22:00:00.000Z

Which is probably not the desired result.

The reason for this is explained on the MDN site:

Where Date is called as a constructor with more than one argument, if values are greater than their logical range (e.g. 13 is provided as the month value or 70 for the minute value), the adjacent value will be adjusted. E.g. new Date(2013, 13, 1) is equivalent to new Date(2014, 1, 1).


A better way to solve the problem is:

const stringToDate = function(dateString) {
  const [dd, mm, yyyy] = dateString.split("-");
  return new Date(`${yyyy}-${mm}-${dd}`);
};

console.log(stringToDate('04-04-2019'));
// Date 2019-04-04T00:00:00.000Z

console.log(stringToDate('77-78-7980'));
// Invalid Date

This gives you the possibility to handle invalid input.

For example:

const date = stringToDate("77-78-7980");

if (date === "Invalid Date" || isNaN(date)) {
  console.log("It's all gone bad");
} else {
  // Do something with your valid date here
}
James Hibbard
  • 16,490
  • 14
  • 62
  • 74
  • The "better way" parses the values as UTC, which is likely unexpected. It's pretty simple to validate the values by including a check, e.g. [*Check date in JavaScript*](https://stackoverflow.com/questions/6800253/check-date-in-javascript). ;-) – RobG Jul 07 '22 at 13:54
  • Fair point. However, the accepted answer for that question also doesn't take time zones into account. Consequently (for me in my time zone) it considers `new Date(2011,5,29)` to be an invalid date. See here: [Is the Javascript date object always one day off?](https://stackoverflow.com/questions/7556591/is-the-javascript-date-object-always-one-day-off) – James Hibbard Mar 31 '23 at 06:15
3

In my case

new Date("20151102034013".replace(/(\d{4})(\d{2})(\d{2})(\d{2})(\d{2})(\d{2})/, "$1-$2-$3T$4:$5:$6"))

Result: Mon Nov 02 2015 04:40:13 GMT+0100 (CET) then I use .getTime() to work with milliseconds

3

You can also write a date inside the parentheses of the Date() object, like these:

new Date("Month dd, yyyy hh:mm:ss")
new Date("Month dd, yyyy")
new Date(yyyy,mm,dd,hh,mm,ss)
new Date(yyyy,mm,dd)
new Date(milliseconds)
Prisoner ZERO
  • 13,848
  • 21
  • 92
  • 137
2

You can just:

var f = new Date(from.split('-').reverse().join('/'));
2

let dateString  = '13-02-2021' //date string in dd-mm-yyyy format

let dateArray = dateString.split("-");
//dateArray[2] equals to 2021
//dateArray[1] equals to 02
//dateArray[0] equals to 13

// using template literals below

let dateObj = new Date(`${dateArray[2]}-${dateArray[1]}-${dateArray[0]}`);

// dateObj equals to Sat Feb 13 2021 05:30:00 GMT+0530 (India Standard Time)

//I'm from India so its showing GMT+0530

P.S : Always refer docs for basics, MDN or DevDocs

Prem G
  • 162
  • 3
  • 8
2

You can use an external library to help you out.

http://www.mattkruse.com/javascript/date/source.html

getDateFromFormat(val,format);

Also see this: Parse DateTime string in JavaScript

Community
  • 1
  • 1
wesbos
  • 25,839
  • 30
  • 106
  • 143
1

Take a look at Datejs for all those petty date related issues.. You could solve this by parseDate function too

Baz1nga
  • 15,485
  • 3
  • 35
  • 61
0

You could use a Regexp.

var result = /^(\d{2})-(\d{2})-(\d{4})$/.exec($("#datepicker").val());
if (result) {
    from = new Date(
        parseInt(result[3], 10), 
        parseInt(result[2], 10) - 1, 
        parseInt(result[1], 10)
    );
}
ChaosPandion
  • 77,506
  • 18
  • 119
  • 157
-2
new Date().toLocaleDateString();

simple as that, just pass your date to js Date Object

Musakkhir Sayyed
  • 7,012
  • 13
  • 42
  • 65