0
\$\begingroup\$

I have an script that is receiving some JSON and then I am parsing it out using reduce. I am sure there is a more elegant way to do it.

JSON

 var request = {
    "operation":"rate_request",
    // JSON removed to make more readable. 
    "freight":
    {
        "items":
        // here is the array I am targeting
        [{
            "item":"7205",
            "qty":10,
            "units":10,
            "weight":"19.0000",
            "paint_eligible":false
        },
        {
            "item":"7677",
            "qty":10,
            "units":4,
            "weight":"5.0000",
            "paint_eligible":false
        }],
    // more JSON removed
}

Here is function to parse out and then loop through:

function parseItems(json){
    var resultsReduce = new Object()
    var itemKeys = ['item','qty', 'units','weight', 'paint_eligable']
    itemKeys.forEach(function(item){  
        if (item){
            resultsReduce[item] = json.freight.items.reduce(function(array, object) {
                   return array.concat(object[item])
            }, [])
        }
    })
    var itemXML = ''

    for(var i = 0; i < resultsReduce.item.length; i++){
        var weight = Number(resultsReduce['weight'][i])
        var qty = Number(resultsReduce['qty'][i])
        var units = Number(resultsReduce['units'][i])
        itemXML += '<LineItem>'
                + '<PieceCount>' + units * qty + '</PieceCount>'
                + '<NetWeight UOM="Lb">' + weight * qty + '</NetWeight>'
                +'<GrossWeight UOM="Lb">' + weight * qty + '</GrossWeight>'
                + '<FreightClassification>' + '50' + '</FreightClassification>'
                +'</LineItem>'
    }
    return itemXML
}

The parseItems function turn the JSON into an object with arrays:

  {
 "item": [7205,7677],
 "qty": [10,10],
 "units": [10,4],
 "weight": ["19.0000","5.0000"],
 "paint_eligible": [false, false]
 }

Then the function loops through the object (manually by targeting the keys) and loops through the loop of the array. Like I mentioned, I am sure it can be more elegant. Any thoughts on how you would make it cleaner?

\$\endgroup\$
1
\$\begingroup\$

This can be handled with a single Array.prototype.forEach loop. Consider the following:

function parseItems(json){
  var output = '';
  json.freight.items.forEach(function (item) {
    output += `
      <LineItem>
        <PieceCount>${item.units * item.qty}</PieceCount>
        <NetWeight UOM="Lb">${item.weight * item.qty}</NetWeight>
        <GrossWeight UOM="Lb">${item.weight * item.qty}</GrossWeight>
        <FreightClassification>50</FreightClassification>
      </LineItem>`;
  });

  return output;
}

No need to iterate over everything repeatedly for this.

Edit: Made a fiddle for you

| improve this answer | |
\$\endgroup\$
  • \$\begingroup\$ Note I used string interpolation syntax since I think it looks cleaner. Browser compatibility may limit your ability to use it. \$\endgroup\$ – C Smith Jan 9 '17 at 1:43

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.