How does moment.js know when it's object is being serialised?

date, datetime, javascript, momentjs

Solution

When using stringify, an object may define how it gets represented, as shown in this documentation:

From https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/JSON/stringify

toJSON behavior

If an object being stringified has a property named toJSON whose value is a function, then the toJSON method customizes JSON stringification behavior: instead of the object being serialized, the value returned by the toJSON method when called will be serialized.

For example:

var x = {
  foo: 'foo',
  toJSON: function () {
    return 'bar';
  }
};
var json = JSON.stringify({x: x});
//json will be the string '{"x":"bar"}'.

moment.js's documentation (seen here: https://raw.github.com/timrwood/moment/2.0.0/moment.js ) shows that this is indeed supported, here is the exact code

toJSON : function () {
 return moment.utc(this).format('YYYY-MM-DD[T]HH:mm:ss.SSS[Z]');
}

So, that is how it is aware of how to represent itself when being stringified.

Problem

From the moment.js docs moment().toJSON(); When serializing an object to JSON, if there is a Moment object, it will be represented as an ISO8601 string. ``` JSON.stringify({ postDate : moment() }); // {"postDate":"2013-02-04T22:44:30.652Z"} ``` I don't understand how the moment object can detect the function operating on it. How is it able to return a different value when serialised, and when simply stored in an object, or returned as a string?

Original source