Managing Dates and Times Using Moment.js

Working with dates and times has always been a bit cumbersome. I’ve always thought that a JavaScript library for manipulating dates would be quite helpful. It was only recently that I was introduced to Moment.js, the awesome JavaScript library for validating, parsing, and manipulating dates and times.

Getting Started with Moment.js

Moment.js is freely available for download from the project’s home page. Moment.js can be run from the browser as well as from within a Node.js application. In order to use it with Node, install the module using the following command.

npm install moment

Then, simply require() and use it in your application as shown below.

var moment = require('moment');

moment().format();

In order to run Moment from the browser, download the script and include it using a script tag, as shown in the following example. Moment.js creates a global moment object which can be used to access all the date and time parsing and manipulation functionality.

<html>
  <head>
    <script src="moment.js"></script>
    <script>
      moment().format();
    </script>
  </head>
  <body>
  </body>
</html>

Date Formatting

In the past, I recall converting date strings into Date objects, grabbing individual pieces of data, and then performing string concatentations. Moment.js has simplified the process of date conversion to any particular format. Date format conversion with Moment is simple, as shown in the following example.

moment().format('YYYY MM DD'); 

moment() gives the current date and time, while format() converts the current date and time to the specified format. This example formats a date as a four digit year, followed by a space, followed by a two digit month, another space, and a two digit date. You can see this code in action by checking out this demo.

Date Validation

Another annoying task that Moment.js has simplified is date validation. In order to perform validation, simply pass a date string to the moment object, along with the date format, and call the isValid() method. This method returns true if the date is valid, and false otherwise. An example of this is shown below, along with this accompanying demo.

var dateEntered = $('#txtEnteredDate').val();

if (!moment(dateEntered,'MM-DD-YYYY').isValid()) {
  console.log('Invalid Date');
} else {
  console.log('Valid Date');
}

There are a number of other helpful flags in the object returned by moment():

  • overflow – This is set when an overflow occurs. An example would be the 13th month or 32nd day.
  • invalidMonth – Set when the month is invalid, like Jannnuaarry.
  • empty – Set when the entered date contains nothing parsable.
  • nullInput – Set when the entered date is null.

Manipulating Dates

There are a number of options for manipulating the moment object. For example, you can add or subtract days, months, years, etc. This is achieved via the add() and subtract() methods. The following example shows how seven days, months, or weeks are added to the current date.

moment().add('days', 7);    // adds 7 days to current date
moment().add('months', 7);  // adds 7 months to current date
moment().add('years', 7);   // adds 7 years to current date

Similarly, the subtract() method is shown below.

moment().subtract('days', 7);   // subtracts 7 days to current date
moment().subtract('months', 7); // subtracts 7 months to current date
moment().subtract('years', 7);  // subtracts 7 years to current date

Time From Now

Another common task is determining how much time exists between two dates. For calculating time from the current date, Moment.js uses a method named fromNow(). Here is a sample which checks how much time exists from the current time:

moment().fromNow();

This code sample displays “a few seconds ago.” If we supply a date to the moment object it would display the time range from now as per the difference. For example, the following code displays “7 days ago.”

var dateA = moment().subtract('days', 7);
dateA.fromNow();

Time From Another Date

fromNow() is used to compare time to the current date. This is just a special case of from(), which compares two arbitrary dates. An example that utilizes from() is shown below. This code displays “in a day.” You can see this code in action by checking out this demo.

var dateB = moment('2014-12-12');
var dateC = moment('2014-12-11');

console.log(dateB.from(dateC));

Calculating the Difference Between Dates

Moment.js offers a way to calculate the difference between two dates. The difference is calculated in milliseconds by default, but can also be returned in days, months, years, etc. To compute the difference, call the diff() method. This method takes a date as its first argument. The unit of time can be specified using the optional second argument. If this is not included, then milliseconds are used. The following example and demo illustrate how diff() is used.

var dateB = moment('2014-11-11');
var dateC = moment('2014-10-11');

console.log('Difference is ', dateB.diff(dateC), 'milliseconds');
console.log('Difference is ', dateB.diff(dateC, 'days'), 'days');
console.log('Difference is ', dateB.diff(dateC, 'months'), 'months');

Date Queries

Moment.js also provides date comparision methods. These methods are isBefore(), isAfter(), and isSame(). As the names imply, these methods return a Boolean indicating if one date is before, after, or equal to another date. An example that uses isAfter() is shown below.

console.log(moment('2010-09-20').isAfter('2010-10-19')); // returns false
console.log(moment('2010-11-20').isAfter('2010-10-19')); // returns true

There is also an isLeapYear() method that checks for leap years.

International Language Support

Moment.js offers support for international language. You can assign a global language or set the language for a particular moment object. By default, Moment.js supports the English language. If you want to support any other language, then assign the key values of that particlar language to moment.lang. The following example, taken from the Moment.js docs, shows how support can be added for French.

moment.lang('fr', {
  months: 'janvier_février_mars_avril_mai_juin_juillet_août_septembre_octobre_novembre_décembre'.split('_'),
  monthsShort: 'janv._févr._mars_avr._mai_juin_juil._août_sept._oct._nov._déc.'.split('_'),
  weekdays: 'dimanche_lundi_mardi_mercredi_jeudi_vendredi_samedi'.split('_'),
  weekdaysShort: 'dim._lun._mar._mer._jeu._ven._sam.'.split('_'),
  weekdaysMin: 'Di_Lu_Ma_Me_Je_Ve_Sa'.split('_'),
  longDateFormat: {
    LT: 'HH:mm',
    L: 'DD/MM/YYYY',
    LL: 'D MMMM YYYY',
    LLL: 'D MMMM YYYY LT',
    LLLL: 'dddd D MMMM YYYY LT'
  },
  calendar: {
    sameDay: '[Aujourdhui à] LT',
    nextDay: '[Demain à] LT',
    nextWeek: 'dddd [à] LT',
    lastDay: '[Hier à] LT',
    lastWeek: 'dddd [dernier à] LT',
    sameElse: 'L'
  },
  relativeTime: {
    future: 'dans %s',
    past: 'il y a %s',
    s: 'quelques secondes',
    m: 'une minute',
    mm: '%d minutes',
    h: 'une heure',
    hh: '%d heures',
    d: 'un jour',
    dd: '%d jours',
    M: 'un mois',
    MM: '%d mois',
    y: 'une année',
    yy: '%d années'
  },
  ordinal: function (number) {
    return number + (number === 1 ? 'er' : 'ème');
  },
  week: {
    dow: 1, // Monday is the first day of the week.
    doy: 4 // The week that contains Jan 4th is the first week of the year.
  }
});

moment.lang('fr');
console.log(moment(1316116057189).fromNow()); // il y a une heure
moment.lang('en');
console.log(moment(1316116057189).fromNow()); // an hour ago

Here is a demo for the above code.

Conclusion

Moment.js is really an awesome library that simplifies date and time related manipulations and validations. This library simplifies the job of application developers, which is almost always a good thing. In this article, we focused on some of the features of Moment.js which help in parsing, validating, and manipulating the datetimes in the browser and Node.js applications. A number of useful plugins are also available for Moment.js. Plugins like ISO Calendar, Jalaali Calendar, and many more can be found on the official plugin page. For more on Moment.js, the reader is directed to the library’s documentation.

Free book: Jump Start HTML5 Basics

Grab a free copy of one our latest ebooks! Packed with hints and tips on HTML5's most powerful new features.

  • Petit Paul

    On the date validation codepen example I enter “2014/02/31″ and it says “Valid date”! If I type “2014-02-31″ or “2014 02 31″ it says it’s an invalid date. Then again “2014 02 25″ also shows as an invalid date! This is not very intuitive, because one might expect people to input dates with slashes or spaces as separators, and not only dashes. Also the order YYYY MM DD is fixed, though one may expect people to enter MM DD YYYY in the US or DD MM YYYY in Europe. You should therefor provide an example of the correct way to input dates, or separates input for Y, M and D.

    • http://www.techillumination.in Jay

      Thanks for feedback @petitpaul:disqus Have made the correction. :)

  • http://twitter.com/adityamenon90 aditya menon

    Can confirm, this library literally saved my life. Well not literally but you get the idea. JS’s default date handling is abhorrent.