object.js 1.9 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980
  1. export function normalizeKeys(key) {
  2. if (key == null) return [];
  3. if (Array.isArray(key)) return key;
  4. return `${key}`.split('.').filter(Boolean);
  5. }
  6. export function objectGet(obj, rawKey, def) {
  7. const keys = normalizeKeys(rawKey);
  8. let res = obj;
  9. keys.every((key) => {
  10. if (res && typeof res === 'object' && (key in res)) {
  11. res = res[key];
  12. return true;
  13. }
  14. res = def;
  15. return false;
  16. });
  17. return res;
  18. }
  19. export function objectSet(obj, rawKey, val) {
  20. const keys = normalizeKeys(rawKey);
  21. if (!keys.length) return val;
  22. const root = obj || {};
  23. let sub = root;
  24. const lastKey = keys.pop();
  25. keys.forEach((key) => {
  26. sub = sub[key] || (sub[key] = {});
  27. });
  28. if (typeof val === 'undefined') {
  29. delete sub[lastKey];
  30. } else {
  31. sub[lastKey] = val;
  32. }
  33. return root;
  34. }
  35. export function objectPurify(obj) {
  36. // Remove keys with undefined values
  37. if (Array.isArray(obj)) {
  38. obj.forEach(objectPurify);
  39. } else if (obj && typeof obj === 'object') {
  40. obj::forEachEntry(([key, value]) => {
  41. if (typeof value === 'undefined') delete obj[key];
  42. else objectPurify(value);
  43. });
  44. }
  45. return obj;
  46. }
  47. export function objectPick(obj, keys) {
  48. return keys.reduce((res, key) => {
  49. const value = obj ? obj[key] : null;
  50. if (value != null) res[key] = value;
  51. return res;
  52. }, {});
  53. }
  54. // invoked as obj::mapEntry((key, value) => transformedValue)
  55. export function mapEntry(func) {
  56. return Object.entries(this).reduce((res, [key, value]) => {
  57. res[key] = func(key, value);
  58. return res;
  59. }, {});
  60. }
  61. // invoked as obj::forEachEntry(([key, value]) => {})
  62. export function forEachEntry(func) {
  63. if (this) Object.entries(this).forEach(func);
  64. }
  65. // invoked as obj::forEachKey(key => {})
  66. export function forEachKey(func) {
  67. if (this) Object.keys(this).forEach(func);
  68. }
  69. // invoked as obj::forEachValue(value => {})
  70. export function forEachValue(func) {
  71. if (this) Object.values(this).forEach(func);
  72. }