'use strict';
/**
 * A typical comparator for sorting.
 * @callback Comparator
 * @param {any} a
 * @param {any} b
 * @returns {number}
 */

/**
 * Returns a copy of an object, sorted deeply by its keys, without mangling any arrays inside of it.
 * @param {object} obj The unsorted object.
 * @param {Comparator} [comparator] An optional comparator to use to sort the keys.
 * @returns {object} The new sorted object.
 */

function sortObject(obj, comparator) {
  // Arrays
  if (Array.isArray(obj)) {
    var result = [];

    for (var i = 0; i < obj.length; ++i) {
      // Fetch
      var value = obj[i]; // Recurse if object or array

      if (value != null && typeof value === 'object') {
        value = sortObject(value, comparator);
      } // Push


      result.push(value);
    }

    return result;
  } // Objects
  else {
      var _result = {};
      var sortedKeys = Object.keys(obj).sort(comparator);

      for (var _i = 0; _i < sortedKeys.length; ++_i) {
        // Fetch
        var key = sortedKeys[_i];
        var _value = obj[key]; // Recurse if object or array

        if (_value != null && typeof _value === 'object') {
          _value = sortObject(_value, comparator);
        } // Push


        _result[key] = _value;
      }

      return _result;
    }
}

module.exports = sortObject;