* Return a deep copy of the specified object using cloneDeep(parent, depth, circular, prototype). * * This returns a new object with all elements copied from the specified * object. Deep copies are made of objects and arrays so you can do anything * with the returned object without affe
(parent, depth, circular, prototype)
| 516 | * notice shall be included in all copies or substantial portions of the Software. |
| 517 | */ |
| 518 | static cloneDeep(parent, depth, circular, prototype) { |
| 519 | // maintain two arrays for circular references, where corresponding parents |
| 520 | // and children have the same index |
| 521 | const allParents = []; |
| 522 | const allChildren = []; |
| 523 | const util = this; |
| 524 | |
| 525 | if (typeof circular === 'undefined') |
| 526 | circular = true; |
| 527 | |
| 528 | if (typeof depth === 'undefined') |
| 529 | depth = 20; |
| 530 | |
| 531 | // recurse this function so we don't reset allParents and allChildren |
| 532 | function _clone(parent, depth) { |
| 533 | // cloning null always returns null |
| 534 | if (parent === null) |
| 535 | return null; |
| 536 | |
| 537 | if (depth === 0) |
| 538 | return parent; |
| 539 | |
| 540 | let child; |
| 541 | if (typeof parent != 'object') { |
| 542 | return parent; |
| 543 | } |
| 544 | |
| 545 | if (Array.isArray(parent)) { |
| 546 | child = []; |
| 547 | } else if (parent instanceof RegExp) { |
| 548 | child = new RegExp(parent.source, util.getRegExpFlags(parent)); |
| 549 | if (parent.lastIndex) child.lastIndex = parent.lastIndex; |
| 550 | } else if (parent instanceof Date) { |
| 551 | child = new Date(parent.getTime()); |
| 552 | } else if (Buffer.isBuffer(parent)) { |
| 553 | child = Buffer.alloc(parent.length); |
| 554 | parent.copy(child); |
| 555 | return child; |
| 556 | } else if (parent instanceof RawConfig) { |
| 557 | child = parent; |
| 558 | } else { |
| 559 | if (typeof prototype === 'undefined') child = Object.create(Object.getPrototypeOf(parent)); |
| 560 | else child = Object.create(prototype); |
| 561 | } |
| 562 | |
| 563 | if (circular) { |
| 564 | const index = allParents.indexOf(parent); |
| 565 | |
| 566 | if (index !== -1) { |
| 567 | return allChildren[index]; |
| 568 | } |
| 569 | allParents.push(parent); |
| 570 | allChildren.push(child); |
| 571 | } |
| 572 | |
| 573 | for (const i in parent) { |
| 574 | const propDescriptor = Object.getOwnPropertyDescriptor(parent, i); |
| 575 | const hasGetter = ((typeof propDescriptor !== 'undefined') && (typeof propDescriptor.get !== 'undefined')); |
no outgoing calls
no test coverage detected