Take the 2-minute tour ×

I'm thinking this must be a common problem but can't seem to find the solution. Using JSON config files to extend a jQuery object that contains objects and arrays.

For the objects and simple properties, I want to overwrite (as extend does nicely).

For the arrays there may or may not be existing items.

Currently an array just overwrites the first elements

var sourceObj = {propterty:"change Me",anArray:[{name:"first"},{name:"second"}]},
    configJSON = '{"propterty":"New Val","anArray":[{"name":"third"}]}',
    configObj = JSON.parse(configJSON);



This returns:

{propterty:"New Val" , anArray:[{name:"third"},{name:"second"}}

Can I instead get:

{propterty:"New Val",anArray:[{name:"first"},{name:"second"},{name:"third"}]}

while ALSO allowing for updating "first" and "second" objects?

"anArray":[{"name":"second","newProp":"add newProp to second"}]

Could/should extend be modified to compare array items and extend or add based on some rule or set property value such as "name"?

Thanks for any advice or pointers.

share|improve this question
This seems to be the the closest i've found that might do it - stackoverflow.com/questions/3748697/… –  Steve Black Nov 7 '12 at 23:47
The normal use of $.extend is for merging user-supplied options with defaults. In this case, it's usually best for a new property to completely replace the one in the original object; appending array properties doesn't fit in with the way it's typically used. What do you need this for? –  Barmar Nov 8 '12 at 0:00
@Barmar true that is one use case, but there are many others...including extending new functions/methods to jQuery object itself –  charlietfl Nov 8 '12 at 0:27
From $.extend docs :The merge performed by $.extend() is not recursive by default; if a property of the first object is itself an object or array, it will be completely overwritten by a property with the same key in the second object. api.jquery.com/jQuery.extend –  charlietfl Nov 8 '12 at 0:29
@charlietfl He knows that -- he's asking whether it would be reasonable to change that definition. –  Barmar Nov 8 '12 at 0:30

1 Answer 1

up vote 2 down vote accepted

I used this solution http://jsfiddle.net/PmuwV/2/ modified from How can I merge properties of two JavaScript objects dynamically? also from Javascript equivalent of jQuery's extend method

requires isDOMNode() I just added in a jquery merge (yes I feel dirty too) on arrays in which duplicates will need to be cleaned up post merge. The Jquery source for extend does something very similar but i found this to be more readable.

function mergeRecursive() {
  // _mergeRecursive does the actual job with two arguments.
  var _mergeRecursive = function (dst, src) {
    if ( isDOMNode(src) || typeof src!=='object' || src===null) {
      return dst; 

    for ( var p in src ) {

//my added bit here - [SB]
      if ($.isArray(src[p])){
          var dupes = {},
               singles = [];
          $.each(  dst[p], function(i, el) {
             if ((dupes[el.name] > -1) &&  (el.name)) {
                  if (el.name ){
                     dupes[el.name] = i;
         dst[p] = singles;
//the rest is original - [SB]

      if( !src.hasOwnProperty(p) ) continue;
      if ( src[p]===undefined ) continue;
      if ( typeof src[p]!=='object' || src[p]===null) {
        dst[p] = src[p];
      } else if ( typeof dst[p]!=='object' || dst[p]===null ) {
        dst[p] = _mergeRecursive(src[p].constructor===Array ? [] : {}, src[p]); 
      } else {              
        _mergeRecursive(dst[p], src[p]);
    return dst;

  // Loop through arguments and merge them into the first argument. 
  var out = arguments[0];
  if ( typeof out!=='object' || out===null) return out;
  for ( var i=1, il=arguments.length; i<il; i++ ) {
    _mergeRecursive(out, arguments[i]);
  return out;
share|improve this answer
updated at jsfiddle.net/PmuwV/5 to merge duplicate array objects with a particular matching property –  Steve Black Nov 8 '12 at 5:54
Needed something similar so I modified yours a bit to use underscore: codepen.io/clouddueling/pen/nFDCH –  Michael Calkins Dec 15 '13 at 21:44

Your Answer


