mirror of
https://github.com/whoisclebs/lodash.git
synced 2026-01-31 07:17:50 +00:00
Ensure _.merge ignores undefined values of source object properties. [closes #573]
This commit is contained in:
23
lodash.js
23
lodash.js
@@ -1962,7 +1962,8 @@
|
||||
* @returns {Object} Returns the destination object.
|
||||
*/
|
||||
function baseMerge(object, source, callback, stackA, stackB) {
|
||||
(isArrayLike(source) ? arrayEach : baseForOwn)(source, function(srcValue, key, source) {
|
||||
var isSrcArr = isArrayLike(source);
|
||||
(isSrcArr ? arrayEach : baseForOwn)(source, function(srcValue, key, source) {
|
||||
var isArr = srcValue && isArrayLike(srcValue),
|
||||
isObj = srcValue && isPlainObject(srcValue),
|
||||
value = object[key];
|
||||
@@ -1972,10 +1973,9 @@
|
||||
if (typeof result == 'undefined') {
|
||||
result = srcValue;
|
||||
}
|
||||
if (typeof result != 'undefined') {
|
||||
value = result;
|
||||
if (isSrcArr || typeof result != 'undefined') {
|
||||
object[key] = result;
|
||||
}
|
||||
object[key] = value;
|
||||
return;
|
||||
}
|
||||
// avoid merging previously merged cyclic sources
|
||||
@@ -1992,22 +1992,21 @@
|
||||
var result = callback ? callback(value, srcValue, key, object, source) : undefined,
|
||||
isShallow = typeof result != 'undefined';
|
||||
|
||||
if (isShallow) {
|
||||
value = result;
|
||||
} else {
|
||||
value = isArr
|
||||
if (!isShallow) {
|
||||
result = isArr
|
||||
? (isArray(value) ? value : [])
|
||||
: (isPlainObject(value) ? value : {});
|
||||
}
|
||||
// add `source` and associated `value` to the stack of traversed objects
|
||||
// add the source value to the stack of traversed objects
|
||||
// and associate it with its merged value
|
||||
stackA.push(srcValue);
|
||||
stackB.push(value);
|
||||
stackB.push(result);
|
||||
|
||||
// recursively merge objects and arrays (susceptible to call stack limits)
|
||||
if (!isShallow) {
|
||||
baseMerge(value, srcValue, callback, stackA, stackB);
|
||||
baseMerge(result, srcValue, callback, stackA, stackB);
|
||||
}
|
||||
object[key] = value;
|
||||
object[key] = result;
|
||||
});
|
||||
|
||||
return object;
|
||||
|
||||
34
test/test.js
34
test/test.js
@@ -2580,22 +2580,6 @@
|
||||
|
||||
deepEqual(actual, { 'a': 1, 'b': 2, 'c': 3 });
|
||||
});
|
||||
|
||||
if (methodName == 'merge') {
|
||||
test('`_.' + methodName + '` should treat sparse arrays as dense', 2, function() {
|
||||
var array = Array(3);
|
||||
array[0] = 1;
|
||||
array[2] = 3;
|
||||
|
||||
var actual = func([], array),
|
||||
expected = array.slice();
|
||||
|
||||
expected[1] = undefined;
|
||||
|
||||
ok('1' in actual);
|
||||
deepEqual(actual, expected);
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
/*--------------------------------------------------------------------------*/
|
||||
@@ -6365,6 +6349,20 @@
|
||||
ok(actual.bar.b === actual.foo.b && actual.foo.b.foo.c === actual.foo.b.foo.c.foo.b.foo.c);
|
||||
});
|
||||
|
||||
test('should treat sources that are sparse arrays as dense', 2, function() {
|
||||
var array = Array(3);
|
||||
array[0] = 1;
|
||||
array[2] = 3;
|
||||
|
||||
var actual = _.merge([], array),
|
||||
expected = array.slice();
|
||||
|
||||
expected[1] = undefined;
|
||||
|
||||
ok('1' in actual);
|
||||
deepEqual(actual, expected);
|
||||
});
|
||||
|
||||
test('should not treat `arguments` objects as plain objects', 1, function() {
|
||||
var object = {
|
||||
'args': args
|
||||
@@ -6389,8 +6387,8 @@
|
||||
});
|
||||
|
||||
test('should not assign `undefined` values', 1, function() {
|
||||
var actual = _.merge({ 'a': 1 }, { 'a': undefined });
|
||||
strictEqual(actual.a, 1);
|
||||
var actual = _.merge({ 'a': 1 }, { 'a': undefined, 'b': undefined });
|
||||
deepEqual(actual, { 'a': 1 });
|
||||
});
|
||||
|
||||
test('should handle merging if `callback` returns `undefined`', 1, function() {
|
||||
|
||||
Reference in New Issue
Block a user