Search code examples
javascriptjsonhierarchical

Hierarchical json from flat with parent ID


http://jsfiddle.net/eYgGK/

I stole this script from a different post:

function convertToHierarchy() {
  var arry = [
    { "Id": "1", "Name": "abc", "Parent": "", "attr": "abc" },
    { "Id": "2", "Name": "abc", "Parent": "1", "attr": "abc" },
    { "Id": "3", "Name": "abc", "Parent": "2", "attr": "abc" },
    { "Id": "4", "Name": "abc", "Parent": "2", "attr": "abc" }
  ];
  var nodeObjects = createStructure(arry);
  for (var i = nodeObjects.length - 1; i >= 0; i--) {
    var currentNode = nodeObjects[i];
    if (currentNode.value.Parent === "") {
      continue;
    }
    var parent = getParent(currentNode, nodeObjects);

    if (parent === null) {
      continue;
    }

    parent.children.push(currentNode);
    nodeObjects.splice(i, 1);
  }
  console.dir(nodeObjects);
  return nodeObjects;
}

function createStructure(nodes) {
  var objects = [];

  for (var i = 0; i < nodes.length; i++) {
    objects.push({
      value: nodes[i],
      children: []
    });
  }

  return objects;

}

function getParent(child, nodes) {
  var parent = null;

  for (var i = 0; i < nodes.length; i++) {
    if (nodes[i].value.Id === child.value.Parent) {
      return nodes[i];
    }
  }

  return parent;
}

This script produces:

[{
    "value": {
        "Id": "1",
        "Name": "abc",
        "Parent": "",
        "attr": "abc"
    },
    "children": [{
        "value": {
            "Id": "2",
            "Name": "abc",
            "Parent": "1",
            "attr": "abc"
        },
        "children": [{
            "value": {
                "Id": "4",
                "Name": "abc",
                "Parent": "2",
                "attr": "abc"
            },
            "children": []
        }, {
            "value": {
                "Id": "3",
                "Name": "abc",
                "Parent": "2",
                "attr": "abc"
            },
            "children": []
        }]
    }]
}]

What I'm looking for is:

[{
    "Id": "1",
    "Name": "abc",
    "Parent": "",
    "attr": "abc",
    "children": [{

        "Id": "2",
        "Name": "abc",
        "Parent": "1",
        "attr": "abc",
        "children": [{

            "Id": "4",
            "Name": "abc",
            "Parent": "2",
            "attr": "abc"
        }, {

            "Id": "3",
            "Name": "abc",
            "Parent": "2",
            "attr": "abc"
           
        }]
    }]
}]

I need to get rid of "value" wrapper primarily, and the empty child node secondarily. I know I can write a clean up script, but that would be less than best practice. Would be great if someone knows how to fix, or suggest a different script!

Thanks


Solution

  • Try something like

    var arry = [{ "Id": "1", "Name": "abc", "Parent": "", "attr": "abc" },
                   { "Id": "2", "Name": "abc", "Parent": "1", "attr": "abc" },
                   { "Id": "3", "Name": "abc", "Parent": "2", "attr": "abc" },
                   { "Id": "4", "Name": "abc", "Parent": "2", "attr": "abc" }];
    
    function convert(array){
        var map = {};
        for(var i = 0; i < array.length; i++){
            var obj = array[i];
            obj.items= [];
    
            map[obj.Id] = obj;
    
            var parent = obj.Parent || '-';
            if(!map[parent]){
                map[parent] = {
                    items: []
                };
            }
            map[parent].items.push(obj);
        }
    
        return map['-'].items;
    
    }
    
    var r = convert(arry)
    

    Demo: Fiddle

    Result

    [{
        "Id" : "1",
        "Name" : "abc",
        "Parent" : "",
        "attr" : "abc",
        "children" : [{
                    "Id" : "2",
                    "Name" : "abc",
                    "Parent" : "1",
                    "attr" : "abc",
                    "children" : [{
                                "Id" : "3",
                                "Name" : "abc",
                                "Parent" : "2",
                                "attr" : "abc",
                                "children" : []
                            }, {
                                "Id" : "4",
                                "Name" : "abc",
                                "Parent" : "2",
                                "attr" : "abc",
                                "children" : []
                            }]
                }]
    }]