You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
36 lines
1.1 KiB
36 lines
1.1 KiB
import { isArray, isPlainObject } from 'is-what'; |
|
|
|
function assignProp(carry, key, newVal, originalObject, includeNonenumerable) { |
|
const propType = {}.propertyIsEnumerable.call(originalObject, key) ? "enumerable" : "nonenumerable"; |
|
if (propType === "enumerable") |
|
carry[key] = newVal; |
|
if (includeNonenumerable && propType === "nonenumerable") { |
|
Object.defineProperty(carry, key, { |
|
value: newVal, |
|
enumerable: false, |
|
writable: true, |
|
configurable: true |
|
}); |
|
} |
|
} |
|
function copy(target, options = {}) { |
|
if (isArray(target)) { |
|
return target.map((item) => copy(item, options)); |
|
} |
|
if (!isPlainObject(target)) { |
|
return target; |
|
} |
|
const props = Object.getOwnPropertyNames(target); |
|
const symbols = Object.getOwnPropertySymbols(target); |
|
return [...props, ...symbols].reduce((carry, key) => { |
|
if (isArray(options.props) && !options.props.includes(key)) { |
|
return carry; |
|
} |
|
const val = target[key]; |
|
const newVal = copy(val, options); |
|
assignProp(carry, key, newVal, target, options.nonenumerable); |
|
return carry; |
|
}, {}); |
|
} |
|
|
|
export { copy };
|
|
|