8000
Sample Input
const obj1 = { "appName": "React", "tags": ["react", 'mfe'], "fields": { "appName": {"type": "checkbox"}, "template": {"type": "textbox","options": [{"label": "opt1"}, {}, {"label": "opt3","value": "value3"}, {"label": "opt4","value": "value4"},{"label": "opt5","value": "value5"}]}, "projectName": {"type": "textbox"} } } const obj2 = { "appName": "React", "tags": ["frontend"], "fields": { "appName": {"type": "checkbox","value": true,"label": "Confirm"}, "template": {"type": "radio","options": [{"value": "value1"},{"label": "opt2","value": "value2"}, {}, {"label": "opt4","value": "value4"}]}, "skipInstall": {"type": "checkbox","label": "Should Skip Install ?"} } }
Expected Output
{ "appName": "React", "tags": ["react", "frontend", "mfe"], "fields": { "appName": { "type": "checkbox", "value": true, "label": "Confirm" }, "template": { "type": "radio", "options": [ { "label": "opt1", "value": "value1" }, { "label": "opt2", "value": "value2" }, { "label": "opt3", "value": "value3" }, { "label": "opt4", "value": "value4" }, { "label": "opt5", "value": "value5" } ] }, "projectName": { "type": "textbox" }, "skipInstall": { "type": "checkbox", "label": "Should Skip Install ?" } } }
But What I get is
{ "appName": "React", "tags": ["frontend"], "fields": { "appName": { "type": "checkbox", "value": true, "label": "Confirm" }, "template": { "type": "radio", "options": [ { "value": "value1" }, { "label": "opt2", "value": "value2" }, {}, { "label": "opt4", "value": "value4" } ] }, "skipInstall": { "type": "checkbox", "label": "Should Skip Install ?" } } }
I believe you want to be using just-extend, not just-merge. Try extend(true, obj1, obj2).
just-extend
just-merge
extend(true, obj1, obj2)
Tried that as well. still not getting the expected result
What is the difference between expected and what you are getting exactly?
{ "appName": "React", "tags": ["frontend", "mfe"], "fields": { "appName": { "type": "checkbox", "value": true, "label": "Confirm" }, "template": { "type": "radio", "options": [ { "label": "opt1", "value": "value1" }, { "label": "opt2", "value": "value2" }, { "label": "opt3", "value": "value3" }, { "label": "opt4", "value": "value4" }, { "label": "opt5", "value": "value5" } ] }, "projectName": { "type": "textbox" }, "skipInstall": { "type": "checkbox", "label": "Should Skip Install ?" } } }
Have already share u what I get and what is expected. the arrays are not merging. its just replacing it on index.
This is what I get
{ "appName": "React", "tags": ["frontend"], "fields": { "appName": { "type": "checkbox", "value": true, "label": "Confirm" }, "template": { "type": "radio", "options": [{ "value": "value1" }, { "label": "opt2", "value": "value2" }, {}, { "label": "opt4", "value": "value4" }] }, "skipInstall": { "type": "checkbox", "label": "Should Skip Install ?" } } }
Ah yeah I was also noticing that! But in your "expected" version you left a bit with that behavior so I thought that is what you wanted.
const isArray = (val: unknown) => !!(val && typeof val === 'object' && Array.isArray(val)); const isPlainObject = (val: unknown) => !!(val && typeof val === 'object' && !isArray(val)); const isCollection = (val: unknown): val is Array<object> => !!(val && isArray(val) && val.length && val.every(isPlainObject)); const isMatrix = (val: unknown): val is Array<unknown[]> => !!(val && isArray(val) && val.length && val.every(isArray)); const isPrimitive = (val: unknown) => !!(val && typeof val !== 'object'); const getValuesByKey = (args: object[], keyName: string) => args .map((obj) => Object.entries(obj) .filter(([key]) => key === keyName) .map(([, value]) => value) ) .flat(); const getValuesByIndex = (args: Array<unknown[]>, index: number) => args.map((arr) => arr[index]).flat(); function mergeDeep(...args: unknown[]): object | unknown[] { if (isCollection(args)) { const allKeys = args.map((obj) => Object.entries(obj).map(([key]) => key)).flat(); const entries = allKeys.map((key) => { const values = getValuesByKey(args as object[], key); return values.every(isPrimitive) ? [key, values[values.length - 1]] : [key, mergeDeep(...values)]; }); return Object.fromEntries(entries); } if (isMatrix(args)) { const maxArrayLength = args.reduce((acc, item) => (acc >= item.length ? acc : item.length), 0); return [...Array(maxArrayLength).keys()].map((index) => mergeDeep(...getValuesByIndex(args, index))).flat(); } return [...new Set(args)].filter(Boolean); } export default mergeDeep;
This is what I have comeup with. Feel free to use it for merge or expand
Activity
uncenter commentedon Jul 21, 2024
I believe you want to be using
just-extend, notjust-merge. Tryextend(true, obj1, obj2).R35007 commentedon Jul 21, 2024
Tried that as well. still not getting the expected result
uncenter commentedon Jul 21, 2024
What is the difference between expected and what you are getting exactly?
R35007 commentedon Jul 21, 2024
Have already share u what I get and what is expected.
the arrays are not merging. its just replacing it on index.
R35007 commentedon Jul 21, 2024
This is what I get
{ "appName": "React", "tags": ["frontend"], "fields": { "appName": { "type": "checkbox", "value": true, "label": "Confirm" }, "template": { "type": "radio", "options": [{ "value": "value1" }, { "label": "opt2", "value": "value2" }, {}, { "label": "opt4", "value": "value4" }] }, "skipInstall": { "type": "checkbox", "label": "Should Skip Install ?" } } }uncenter commentedon Jul 21, 2024
Ah yeah I was also noticing that! But in your "expected" version you left a bit with that behavior so I thought that is what you wanted.
R35007 commentedon Jul 21, 2024
This is what I have comeup with. Feel free to use it for merge or expand