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.

49 lines
1023 B

4 years ago
  1. 'use strict';
  2. /**
  3. * Module dependenices
  4. */
  5. const clone = require('shallow-clone');
  6. const typeOf = require('kind-of');
  7. const isPlainObject = require('is-plain-object');
  8. function cloneDeep(val, instanceClone) {
  9. switch (typeOf(val)) {
  10. case 'object':
  11. return cloneObjectDeep(val, instanceClone);
  12. case 'array':
  13. return cloneArrayDeep(val, instanceClone);
  14. default: {
  15. return clone(val);
  16. }
  17. }
  18. }
  19. function cloneObjectDeep(val, instanceClone) {
  20. if (typeof instanceClone === 'function') {
  21. return instanceClone(val);
  22. }
  23. if (instanceClone || isPlainObject(val)) {
  24. const res = new val.constructor();
  25. for (let key in val) {
  26. res[key] = cloneDeep(val[key], instanceClone);
  27. }
  28. return res;
  29. }
  30. return val;
  31. }
  32. function cloneArrayDeep(val, instanceClone) {
  33. const res = new val.constructor(val.length);
  34. for (let i = 0; i < val.length; i++) {
  35. res[i] = cloneDeep(val[i], instanceClone);
  36. }
  37. return res;
  38. }
  39. /**
  40. * Expose `cloneDeep`
  41. */
  42. module.exports = cloneDeep;