Browse Source

[object.merge]: add function

mightyplow 7 years ago
parent
commit
052a8b2a72
4 changed files with 79 additions and 0 deletions
  1. 1 0
      src/index.js
  2. 47 0
      src/object/__tests__/merge.test.js
  3. 1 0
      src/object/index.js
  4. 30 0
      src/object/merge.js

+ 1 - 0
src/index.js

@@ -35,6 +35,7 @@ export {
     extract,
     filter,
     fromArray,
+    merge,
     prop,
     removeProp
 } from './object';

+ 47 - 0
src/object/__tests__/merge.test.js

@@ -0,0 +1,47 @@
+import merge from '../merge';
+
+export default (test) => {
+    const a = {
+        foo: 'foo',
+        bar: {
+            foo: 'foo'
+        },
+        baz: [1],
+        blubb: {
+            foo: {
+                bar: 'bar'
+            }
+        }
+    };
+
+    const b = {
+        foo: 'foob',
+        bar: {
+            second: 1
+        },
+        baz: [2],
+        blubb: {
+            foo: {
+                foo: 'foo'
+            }
+        }
+    };
+
+    const expected = {
+        foo: 'foob',
+        bar: {
+            foo: 'foo',
+            second: 1
+        },
+        baz: [1, 2],
+        blubb: {
+            foo: {
+                bar: 'bar',
+                foo: 'foo'
+            }
+        }
+    };
+
+    test.ok(JSON.stringify(merge(a, b)) === JSON.stringify(expected), 'objects should be merged');
+    test.done();
+}

+ 1 - 0
src/object/index.js

@@ -5,5 +5,6 @@ export { default as defaults } from './defaults';
 export { default as extract } from './extract';
 export { default as fromArray } from './fromArray';
 export { default as filter } from './filter';
+export { default as merge } from './merge';
 export { default as prop } from './prop';
 export { default as removeProp } from './removeProp';

+ 30 - 0
src/object/merge.js

@@ -0,0 +1,30 @@
+/**
+ * Merges too objects deeply.
+ *
+ * @memberOf object
+ * @function
+ * @param {Object} targetObject
+ * @param {Object[]} objects
+ * @return {Object}
+ */
+const merge = (targetObject, ...objects) => {
+    return objects.reduce((targetObject, object) => {
+        return Object.entries(object).reduce((targetObject, [key, value]) => {
+            if (key in targetObject) {
+                if (Array.isArray(value)) {
+                    targetObject[key] = targetObject[key].concat(value);
+                } else if (typeof value === 'object') {
+                    merge(targetObject[key], value);
+                } else {
+                    targetObject[key] = value;
+                }
+            } else {
+                targetObject[key] = value;
+            }
+
+            return targetObject;
+        }, targetObject);
+    }, targetObject);
+};
+
+export default merge;