Search code examples
javascriptobjectdefault-value

Defaults with nested object


Suppose I have the following object which provides the default value:

default_values = {a: 0, b: 0, c: {aa: 0, bb: 0}}

I also have another object that would override some of these default values:

override_values = {a: 5, c: {aa: 5}}

What I'd like to have is to combine these two objects that would result in

combined: {a: 5, b: 0, c: {aa: 5, bb: 0}}

However, using the regular spread operator like {...default_values, ...override_values} would just give c: {aa: 5} instead of c: {aa: 5, bb: 0}. The object could be huge so I can't hard-code all the nested objects.

I could write a function to basically go over each key... if the value is not an object then use override | default, otherwise recursively call this function on the nested object. But I feel like this is very common that there's already something like this.


Solution

  • You're looking for something along the lines of deep_merge or merge. These functions are widely and are presented in lodash library.

    Here is an example of it:-

    function merge(target, source) {
      Object.keys(source).forEach(key => {
        const sourceValue = source[key];
        if (sourceValue) {
          const targetValue = target[key];
          const newValues = merge(targetValue, sourceValue);
          Object.assign(sourceValue, newValues);
        }
      });
    
      Object.assign(target || {}, source);
      return target;
    }