0

I have two JSON objects and I want to merge them:

Object1: {"9":{"322":{"option0":"177"}}}
Object2: {"10":{"323":{"option":"456"}}}

And I want for final result to be like:

{
    "9": {
        "322": {
            "option0": "177"
        }
    },
    "10": {
        "323": {
            "option": "456"
        }
    }
}

I tried the concat method, but the result is this:

{
    "9":{
        "322":{
            "option0":"177"
        }
    }
}
{
    "10":{
        "323":{
            "option":"456"
        }
    }
}

PS: The objects are taken by input like so:

var object1 = $('input').val();
ADyson
  • 57,178
  • 14
  • 51
  • 63
zagzter
  • 229
  • 1
  • 11
  • Hi! Please take the [tour] (you get a badge!) and read through the [help], in particular [*How do I ask a good question?*](/help/how-to-ask) Your best bet here is to do your research, [search](/help/searching) for related topics on SO, and give it a go. ***If*** you get stuck and can't get unstuck after doing more research and searching, post a [mcve] of your attempt and say specifically where you're stuck. People will be glad to help. – T.J. Crowder Sep 20 '18 at 09:24
  • 3
    Side note: JSON is a *textual notation* for data exchange. [(More here.)](http://stackoverflow.com/a/2904181/157247) If you're dealing with JavaScript source code, and not dealing with a *string*, you're not dealing with JSON. You've said you've used `concat`, so you're not dealing with a string. – T.J. Crowder Sep 20 '18 at 09:25
  • 1
    Could you give a clearer example of the input in the first example. Your description states they are arrays, yet the output would indicate they are objects. – Rory McCrossan Sep 20 '18 at 09:25
  • thanks guys, I've change it. – zagzter Sep 20 '18 at 09:36
  • And also these are just `objects` there's no such a JSON object. – cнŝdk Sep 20 '18 at 09:38
  • @zagzter thanks the clarification re the input boxes. I've updated my answer to work on that basis - take a look. – ADyson Sep 20 '18 at 09:42

4 Answers4

3

Use Object.assign()

const Array1 = {"9":{"322":{"option0":"177"}}}
const Array2 = {"10":{"323":{"option":"456"}}}

let newObject = Object.assign({}, Array1, Array2);

console.log(newObject);
2

ES6 way:

const object1 = {"9":{"322":{"option0":"177"}}}
const object2 = {"10":{"323":{"option":"456"}}}

const object3 = { ...object1, ...object2 }

console.log(object3)

Codepen:

https://codepen.io/anon/pen/eLxBdK?editors=0001

Use ES6 syntax whenever possible.

  • shorter code
  • more readable usually
  • this case in particular allows you to easily do deep merges (which was a pain before)
  • faster
azrahel
  • 1,143
  • 2
  • 13
  • 31
  • But do not you will have to compile with Babel if you want any IE/Edge support – mplungjan Sep 20 '18 at 09:57
  • Am kinda radical on that. IE is evil. Edge actually supports spread operator: https://kangax.github.io/compat-table/es6/ I would rather boycott IE since it s so slow on implementing main language of the WWW new features comparing to all other browsers (and always have been so) Just an opinion in sea of opinions, dont start a war over it please :D – azrahel Sep 20 '18 at 10:02
  • and of course, you are right about IE - you need Babel in its case – azrahel Sep 20 '18 at 10:02
  • and I also added **whenever possible** in my post. Sometimes there are some limitations (like IE limitations) – azrahel Sep 20 '18 at 10:04
  • Meantime in the real world we have to support the default browser – mplungjan Sep 20 '18 at 10:07
  • not sure about your *real* but in everybody elses world IE is used by 3% of users :) http://gs.statcounter.com/browser-market-share That is **not** default. You work for IE or what? – azrahel Sep 20 '18 at 10:15
  • browser wars ftw <3 – azrahel Sep 20 '18 at 10:16
  • Among those 3% (IE10 or lower) of our users, there are several that could write emails to the top management and complain... – mplungjan Sep 20 '18 at 10:59
  • I just realise that MSIE in the user agent are IE<11 - so currently one third of accesses are IE11 useragents - and we are mostly accessed by Desktops - where your site quotes 7%IE - [higher in Europe](http://gs.statcounter.com/browser-market-share/desktop/europe), even [higher in the US](http://gs.statcounter.com/browser-market-share/desktop/north-america) – mplungjan Sep 20 '18 at 11:03
  • sure, altogether I of course know that most of the projects need and DO support IE11. And usually support/dont support is not my decision anyway. Am just theorizing in the end: ) ES6 is becoming a standard more and more as well as tons of project use Babel which is not big overhead usually. – azrahel Sep 20 '18 at 11:28
  • As long as you are not thinking that 3% is the actual % :) – mplungjan Sep 20 '18 at 11:29
1

Actually these are objects and not JSON Arrays, and you got an array as result because Array#concat() will return an array and what you want is an object.

So what you can do is to use Object.assign() method:

let obj = Object.assign({}, JSON.parse(o1), JSON.parse(o2));

Note:

If you take these objects from input, you will be getting them as strings you need to parse them with JSON.parse() to getb the right objects.

let o1  = '{"9":{"322":{"option0":"177"}}}';
let o2 =  '{"10":{"323":{"option":"456"}}}';

let obj = Object.assign({}, JSON.parse(o1), JSON.parse(o2));

console.log(obj);
cнŝdk
  • 31,391
  • 7
  • 56
  • 78
  • 1
    @mplungjan I did, I just wanted to mention that these aren't arrays. – cнŝdk Sep 20 '18 at 09:30
  • @zagzter If you are taking them from the input so they will be `strings` you need to parse them first, so they will be `objects`. Check my update. – cнŝdk Sep 20 '18 at 09:40
  • @zagzter And to get the result object back as a `string` and use it in an `input` val, you need to use `$("#input").val(JSON.stringify(obj))`.. – cнŝdk Sep 20 '18 at 09:52
1

Since you are getting the values from a text field, they will initially be JSON strings. In order to treat them like objects and merge then you need to parse them first. Then you can achieve your desired output using jQuery's $.extend() method, which merges one object into another.

Demo:

var obj1 = JSON.parse($("#obj1").val());
var obj2 = JSON.parse($("#obj2").val());
var merged= $.extend({}, obj1, obj2);
console.log(merged);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type="text" id="obj1" value='{"9":{"322":{"option0":"177"}}}'/>
<input type="text" id="obj2" value='{"10":{"323":{"option":"456"}}}'/>

Documentation: https://api.jquery.com/jquery.extend/

ADyson
  • 57,178
  • 14
  • 51
  • 63