mirror of
https://github.com/whoisclebs/lodash.git
synced 2026-02-11 19:37:49 +00:00
Make iteration fix in _.keysIn less constructor specific.
This commit is contained in:
@@ -8049,7 +8049,7 @@
|
|||||||
}
|
}
|
||||||
if (support.nonEnumShadows && object !== objectProto) {
|
if (support.nonEnumShadows && object !== objectProto) {
|
||||||
var className = object === stringProto ? stringClass : object === errorProto ? errorClass : toString.call(object),
|
var className = object === stringProto ? stringClass : object === errorProto ? errorClass : toString.call(object),
|
||||||
nonEnum = nonEnumProps[className] || nonEnumProps[objectClass];
|
nonEnums = nonEnumProps[className] || nonEnumProps[objectClass];
|
||||||
|
|
||||||
if (className == objectClass) {
|
if (className == objectClass) {
|
||||||
proto = objectProto;
|
proto = objectProto;
|
||||||
@@ -8057,8 +8057,9 @@
|
|||||||
length = shadowedProps.length;
|
length = shadowedProps.length;
|
||||||
while (length--) {
|
while (length--) {
|
||||||
key = shadowedProps[length];
|
key = shadowedProps[length];
|
||||||
if (!(isProto && nonEnum[key]) &&
|
var nonEnum = nonEnums[key];
|
||||||
(key == 'constructor' ? hasOwnProperty.call(object, key) : object[key] !== proto[key])) {
|
if (!(isProto && nonEnum) &&
|
||||||
|
(nonEnum ? hasOwnProperty.call(object, key) : object[key] !== proto[key])) {
|
||||||
result.push(key);
|
result.push(key);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
71
test/test.js
71
test/test.js
@@ -4535,36 +4535,6 @@
|
|||||||
deepEqual(props.sort(), shadowedProps);
|
deepEqual(props.sort(), shadowedProps);
|
||||||
});
|
});
|
||||||
|
|
||||||
test('`_.' + methodName + '` does not iterate over non-enumerable properties (test in IE < 9)', 10, function() {
|
|
||||||
_.forOwn({
|
|
||||||
'Array': arrayProto,
|
|
||||||
'Boolean': Boolean.prototype,
|
|
||||||
'Date': Date.prototype,
|
|
||||||
'Error': errorProto,
|
|
||||||
'Function': funcProto,
|
|
||||||
'Object': objectProto,
|
|
||||||
'Number': Number.prototype,
|
|
||||||
'TypeError': TypeError.prototype,
|
|
||||||
'RegExp': RegExp.prototype,
|
|
||||||
'String': stringProto
|
|
||||||
},
|
|
||||||
function(proto, key) {
|
|
||||||
var message = 'non-enumerable properties on ' + key + '.prototype',
|
|
||||||
props = [];
|
|
||||||
|
|
||||||
func(proto, function(value, prop) { props.push(prop); });
|
|
||||||
|
|
||||||
if (/Error/.test(key)) {
|
|
||||||
ok(_.every(['constructor', 'toString'], function(prop) {
|
|
||||||
return !_.contains(props, prop);
|
|
||||||
}), message);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
deepEqual(props, [], message);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
test('`_.' + methodName + '` skips the prototype property of functions (test in Firefox < 3.6, Opera > 9.50 - Opera < 11.60, and Safari < 5.1)', 2, function() {
|
test('`_.' + methodName + '` skips the prototype property of functions (test in Firefox < 3.6, Opera > 9.50 - Opera < 11.60, and Safari < 5.1)', 2, function() {
|
||||||
function Foo() {}
|
function Foo() {}
|
||||||
Foo.prototype.a = 1;
|
Foo.prototype.a = 1;
|
||||||
@@ -7094,6 +7064,47 @@
|
|||||||
deepEqual(func(new Foo).sort(), actual);
|
deepEqual(func(new Foo).sort(), actual);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test('`_.' + methodName + '` skips non-enumerable properties (test in IE < 9)', 50, function() {
|
||||||
|
_.forOwn({
|
||||||
|
'Array': arrayProto,
|
||||||
|
'Boolean': Boolean.prototype,
|
||||||
|
'Date': Date.prototype,
|
||||||
|
'Error': errorProto,
|
||||||
|
'Function': funcProto,
|
||||||
|
'Object': objectProto,
|
||||||
|
'Number': Number.prototype,
|
||||||
|
'TypeError': TypeError.prototype,
|
||||||
|
'RegExp': RegExp.prototype,
|
||||||
|
'String': stringProto
|
||||||
|
},
|
||||||
|
function(proto, key) {
|
||||||
|
_.each([proto, _.create(proto)], function(object, index) {
|
||||||
|
var actual = func(proto),
|
||||||
|
isErr = /Error/.test(key),
|
||||||
|
message = 'enumerable properties ' + (index ? 'inherited from' : 'on') + ' `' + key + '.prototype`',
|
||||||
|
props = isErr ? ['constructor', 'toString'] : ['constructor'];
|
||||||
|
|
||||||
|
actual = isErr ? _.difference(props, actual) : actual;
|
||||||
|
strictEqual(_.isEmpty(actual), !isErr, 'skips non-' + message);
|
||||||
|
|
||||||
|
proto.a = 1;
|
||||||
|
actual = func(object);
|
||||||
|
delete proto.a;
|
||||||
|
|
||||||
|
strictEqual(_.contains(actual, 'a'), !(isKeys && index), 'includes ' + message);
|
||||||
|
|
||||||
|
if (index) {
|
||||||
|
object.constructor = 1;
|
||||||
|
if (isErr) {
|
||||||
|
object.toString = 2;
|
||||||
|
}
|
||||||
|
actual = func(object);
|
||||||
|
ok(_.isEmpty(_.difference(props, actual)), 'includes shadowed properties on objects that inherit from `' + key + '.prototype`');
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
test('`_.' + methodName + '` skips the prototype property of functions (test in Firefox < 3.6, Opera > 9.50 - Opera < 11.60, and Safari < 5.1)', 2, function() {
|
test('`_.' + methodName + '` skips the prototype property of functions (test in Firefox < 3.6, Opera > 9.50 - Opera < 11.60, and Safari < 5.1)', 2, function() {
|
||||||
function Foo() {}
|
function Foo() {}
|
||||||
Foo.a = 1;
|
Foo.a = 1;
|
||||||
|
|||||||
Reference in New Issue
Block a user