JSON.stringify()

stringify() is a method in JSON object which converts a value (Eg: Object, Number, Array etc) to a string in UTF-16 encoded JSON format. Few use cases are converting data to string when sending to the server via fetch or storing the data in localStorage by converting it to string etc,.

JSON.stringify accepts 3 parameters:

Points to remember:

Let's see an example of how JSON.stringify method works.

var myObj = {
  random: 73,
  'random float': 93.655,
  isAlive: true,
  date: '1987-03-11',
  firstname: 'Myrtice',
  lastname: 'Rosalba',
  city: 'Amritsar',
  countryCode: 'MP',
  nullValue: null,
  array: ['Georgina', 'Lolita', 'Shandie', 'Deirdre', 'Lynea'],
  'array of objects': [
    {
      index: 0,
      'index start at 5': 5,
    },
    {
      index: 1,
      'index start at 5': 6,
    },
    {
      index: 2,
      'index start at 5': 7,
    },
  ],
};

// String replacer function
function stringReplacer(key, value) {
  if (typeof value === 'string') {
    return undefined;
  }

  return value;
}

// Logs formatted json object
console.log(JSON.stringify(myObj));

// Logs only formatted number, boolean, null value in json object
console.log(JSON.stringify(myObj, stringReplacer));

// Logs formatted 2 spaced json object
console.log(JSON.stringify(myObj, undefined, 2));

Now that we have seen what is the output of JSON.stringify method and how it works, lets implement it by starting with serializing values.

Serializing values

For starters, we will start with the following data types.

  1. Undefined
  2. Number
  3. Boolean
  4. String
function stringify(value) {
  // Type of the value argument
  var type = typeof value;

  function getValues(value) {
    if (type === 'undefined') {
      return undefined;
    }

    if (type === 'number' || type === 'boolean') {
      return '' + value + '';
    }

    if (type === 'string') {
      return '"' + value + '"';
    }
  }

  return getValues(value);
}

console.log(stringify(1)); // "1"

console.log(stringify('abc')); // ""abc""

console.log(stringify(true)); // "true"

// Just undefined instead of "undefined"
console.log(stringify(undefined) === JSON.stringify(undefined)); // true

The above function so far is self-explanatory. All it does is wrap the values with quotes and return it expect for the undefined data type.

Now we will add support for more data types like

To support arrays and objects, we should be able to parse the value up to n level. We have to recursively go up the children and serialize the values.

For arrays its pretty simple, iterate the array with an opening and closing bracket and call the stringify() function which in turn calls the getValues() function and repeat until all the values are accounted for.

But for objects, we need to serialize the value as well as the property (key) with the opening and closing bracket of an object literals.

Also one interesting thing is for date objects, JSON.stringify method returns the value in ISO format.

function stringify(value) {
  var type = typeof value;

  function getValues(value) {
    if (type === 'undefined' || type === 'function') {
      return undefined;
    }

    if (type === 'number' || type === 'boolean') {
      return '' + value + '';
    }

    if (type === 'string') {
      return '"' + value + '"';
    }
  }

  // For object datatype
  // In javascript both array and object are objects (FYI if you didn't know already)
  if (type === 'object') {
    // To check if the value is null
    if (!value) {
      return '' + value + '';
    }

    // To check if the value is date object
    if (value instanceof Date) {
      return '"' + new Date(value).toISOString() + '"'; // return ISO format
    }

    // To check if the value is Array
    if (value instanceof Array) {
      return '[' + value.map(stringify) + ']'; // Call stringify recursively to return its value
    } else {
      // Else it is just an object
      // Call stringify recursively to map key and its value
      return '{' + Object.keys(value).map((key) => '"' + key + '"' + ':' + stringify(value[key])) + '}';
    }
  }

  return getValues(value);
}

console.log(stringify([1, 2, 3])); // "[1,2,3]"

console.log(stringify(new Date())); // prints date in ISO format

console.log(stringify({ a: 1 })); // ""{a:1}""

console.log(stringify(myObj) === JSON.stringify(myObj)); // true

console.log(JSON.parse(stringify(myObj))); // Same as JSON.parse(JSON.stringify(myObj))

The above function now works for all data types and also the output is same as the JSON.stringify method.

Now lets add support for toJSON() method. Just to re-iterate, if an object contains toJSON method and whatever it is returning will be used by JSON.stringify.

var myObj = { toJSON: () => 'a' };

function stringify(value) {
  function getValues(value) {
    // To check if object has `toJSON` method or not
    if (typeof value.toJSON === 'function') {
      return '"' + value.toJSON() + '"';
    }
  }

  return getValues(value);
}

console.log(stringify(myObj)); // ""a""
console.log(stringify(myObj) === JSON.stringify(myObj)); // true

Note: For the sake of this post we will ignore adding support of Symbol datatype, the replacer function, and space argument.

Final thoughts

JSON.stringify method is powerful feature in javascript. Most of us would have used it on regular basis. I have learned more about JSON.stringify method now than before.

Post your comments below if you have any questions. If you liked the post share it.

Follow me on twitter for more web related things. See ya in next post ;)

References

Join 300+ Readers

Sent out once every month. No spam 🤞