There are a number of popular JavaScript date formatting libraries out there, such as Moment.js, Luxon and date-fns. Those libraries are very powerful and useful, allowing you to request various date formats using a special syntax, but they also come with many more features than most people will ever use. And that means, your users are probably downloading more JavaScript then they need to.
In this article, I'm going to show you how to use the built in basic Date object to format dates without any third-party library. In other words, we'll be formatting dates with pure vanilla JavaScript.
Feel free to copy and paste the solutions below to use as a starting point in your own code bases. I'll demonstrate how to generate a number of common format types, but you may need to modify the solutions below a little bit to format dates and times to be exactly the way you want.
What about the Internationalization API?
Before I start, I should mention that there is some formatting functionality built into JavaScript dates, using the Internationalization API.
Using the Internationalization API, you can format dates according to a specific locale, which means formatting according to the customs of the user's location and language. If you're not picky about how dates and times will be displayed, this can work well in many cases, but it depends on each user's operating system, and which locales are installed on their devices. In other words, it can be hard to predict what the format will look like in any given browser.
If you want to format dates in some specific way and have full control over what is being displayed, please read on.
Date methods
Pretty much all the information we need can be provided by a few built-in methods on the date object:
const date = new Date;
date.getFullYear();
date.getMonth();
date.getDate();
date.getDay();
date.getHours();
date.getMinutes();
date.getSeconds();
Now you may have noticed that all these methods return numbers. But how are you supposed to get words out of it like "Thursday" or "November"? And what if you want your month or date number to start with a zero? No problem, we can use JavaScript!
Years
Get the full year
Getting the year out of the Date object is really easy, but it's a four-digit year by default:
date.getFullYear();
What if you want only two-digits?
There is a getYear()
function in the Date object as well, and sometimes I accidently use that instead of getFullYear()
. However, it's more or less useless. In 2019, it returns 119. Why?? Because there is a Y2K bug baked into JavaScript, even though JavaScript was designed in 1995! In those first five years of JavaScript, people could call getYear() for a two-digit year, and simply add 1900 to get a four-digit year. And I guess that still works, because 1900 + 119 = 2019!
Since the getYear()
function has been broken since the year 2000, I recommend getting a two-digit year using this approach instead:
function getTwoDigitYear(date) {
return date.getFullYear() % 100;
}
Months
Display the month as a two-digit number
The getMonth()
function of the Date object returns a number between 0 and 11. That has got to be one of the biggest surprises when working with dates in JavaScript. It also mostly makes this method useless without writing more code. Let's see how to do that.
function getTwoDigitMonth(date) {
const month = date.getMonth() + 1;
if (month < 10) {
return `0${month}`;
} else {
return month.toString();
}
}
Display the month as a string
If we want to display the month as a string of text like "February" or "Mar", then we need to use a JavaScript array with all the months. In fact, this is why the getMonth()
method returns a number between 0 and 11, because arrays start counting at 0 as well!
function getMonthName(date) {
const months = [
'January',
'February',
'March',
'April',
'May',
'June',
'July',
'August',
'September',
'October',
'November',
'December'
];
return months[date.getMonth()];
}
If you want to use a short form of the month, or just a single character, or another language, you can easily adapt the code above to change the contents of the array with whatever you prefer to use.
Days of the week
If you're going to be displaying the day of the week, you'll probably want to be displaying some text. You can use the same approach that we used for formatting months above. Basically, you just need to define an array of text and access it using the getDay()
result as an index.
function getWeekDayName(date) {
const weekDays = [
'Sunday',
'Monday',
'Tuesday',
'Wednesday',
'Thursday',
'Friday',
'Saturday'
];
return weekDays[date.getDay()];
}
Again, if you want to return different text, like 'Sun' or 'S', just replace the entries in the array with whatever you prefer.
Day of the month
The day of the month is pretty straightforward. You can just call getDate()
to get the number, and you don't have to add one to it or anything.
Display the day of the month as a two-digit number
For some date formats, you may want to get a two-digit version of the date number. That's simple enough:
function getTwoDigitDayOfTheMonth(date) {
const dayOfTheMonth = date.getDate();
if (dayOfTheMonth < 10) {
return `0${dayOfTheMonth}`;
} else {
return dayOfTheMonth.toString();
}
}
Display an ordinal with the day of the month
If you want a fancy day of the month with an ordinal after it, like 1st, 2nd, 3rd, 4th, 21st, etc., you can easily figure that out with a switch statement:
function getDayOfTheMonthWithOrdinal(date) {
const dayOfTheMonth = date.getDate();
const ordinal = getOrdinal(dayOfTheMonth);
return `${dayOfTheMonth}${ordinal}`;
}
function getOrdinal(number) {
const lastDigitOfNumber = number % 10;
switch (lastDigitOfNumber) {
case 1:
return 'st';
case 2:
return 'nd';
case 3:
return 'rd';
default:
return 'th';
}
}
Times
You can apply the techniques we used above with times as well, depending what you need. Let's say we want to display a time format in 12-hour time with "am" or "pm", like "9:45pm". Here's how:
function formatTwelveHourTime(date) {
const hour = getHourInTwelveHourClock(date);
const minute = getTwoDigitMinute(date);
const meridiem = getMeridiem(date);
return `${hour}:${minute}${meridiem}`;
}
function getHourInTwelveHourClock(date) {
const hour = date.getHours();
if (hour === 0 || hour === 12) {
return 12;
}
return hour % 12;
}
function getTwoDigitMinute(date) {
const minute = date.getMinutes();
if (minute < 10) {
return `0${minute}`;
} else {
return minute.toString();
}
}
function getMeridiem(date) {
const hour = date.getHours();
if (hour < 12) {
return 'am';
} else {
return 'pm';
}
}
Bringing it all together
We've covered how to generate all the different pieces of various date formats. How about putting all the difference pieces together?
You can use any method you like, but I suggest an approach like the following, using a template string.
function shortDateFormat(date) {
const year = date.getFullYear();
const month = getTwoDigitMonth(date);
const dayOfTheMonth = getTwoDigitDayOfTheMonth(date);
return `${year}-${month}-${dayOfTheMonth}`;
}
You can create as many formatting functions as you have formats to generate. Here's another example:
function longDateTimeFormat(date) {
const weekDayName = getWeekDayName(date);
const monthName = getMonthName(date);
const dayOfTheMonth = getDayOfTheMonthWithOrdinal(date);
const year = date.getFullYear();
const time = formatTwelveHourTime(date);
return `${weekDayName}, ${monthName} ${dayOfTheMonth}, ${year} at ${time}`;
}
Conclusion
I hope I've provided you with all the tools and techniques you might need to format dates and times. You can apply many of these techniques in other ways too, like formatting currencies. More importantly, with a little bit of custom JavaScript, you can avoid having additional dependencies for your project and downloads for your users.
Published on April 19th, 2019. © Jesse Skinner