0

I am trying to build a HTML page using JS. The details of what needs to go into the HTML are sent in a json object from the server. Now the json object is structured in such a way that basically mimics the dom structure and I iterate through the object and fetch individual html element data from it and render the HTML string. The problem occurs when I use a recursive function to run through this object. I trigger a Stack Exceeded Error. I guess this is because of the limit on browser stack size. I would like to understand, what would be the best way I can iterate through this object to create the page without causing the script to fail.

pageObj Structure ->

//only a representation of object, the size is much larger.

{ "Default" : { "#text" : [ "\n  ",
          "\n"
        ],
      "MainForm" : { "#text" : [ "\n    ",
              "\n    ",
              "\n  "
            ],
          "shippingInfo" : { "#text" : [ "\n      ",
                  "\n      ",
                  "\n      ",
                  "\n      ",
                  "\n      ",
                  "\n      ",
                  "\n      ",
                  "\n    "
                ],
              "@attributes" : { "title" : "Shipping Information",
                  "type" : "FormBlock"
                },
              "Row" : [ { "#text" : [ "\n        ",
                        "\n      "
                      ],
                    "fName" : { "@attributes" : { "placeHolder" : "Enter First Name",
                            "title" : "First Name",
                            "type" : "text"
                          } }
                  },
                  { "#text" : [ "\n        ",
                        "\n      "
                      ],
                    "lName" : { "@attributes" : { "placeHolder" : "Enter Last Name",
                            "title" : "Last Name",
                            "type" : "text"
                          } }
                  },
                  { "#text" : [ "\n        ",
                        "\n      "
                      ],
                    "addr1" : { "@attributes" : { "title" : "Address 1",
                            "type" : "text"
                          } }
                  },
                  { "#text" : [ "\n        ",
                        "\n      "
                      ],
                    "addr2" : { "@attributes" : { "title" : "Address 2",
                            "type" : "text"
                          } }
                  },
                  { "#text" : [ "\n        ",
                        "\n        ",
                        "\n      "
                      ],
                    "state" : { "@attributes" : { "title" : "State",
                            "type" : "text"
                          } },
                    "zipCode" : { "@attributes" : { "title" : "Zip Code",
                            "type" : "text"
                          } }
                  },
                  { "#text" : [ "\n        ",
                        "\n        ",
                        "\n      "
                      ],
                    "country" : { "@attributes" : { "title" : "Country",
                            "type" : "text"
                          } },
                    "phone" : { "@attributes" : { "title" : "Phone",
                            "type" : "text"
                          } }
                  },
                  { "#text" : [ "\n        ",
                        "\n        ",
                        "\n        ",
                        "\n        ",
                        "\n      "
                      ],
                    "day10" : { "@attributes" : { "title" : "10 day Shipping ($3)",
                            "type" : "radio"
                          } },
                    "day5" : { "@attributes" : { "title" : "5 Shipping ($10)",
                            "type" : "radio"
                          } },
                    "free" : { "@attributes" : { "title" : "Free Shipping ($0)",
                            "type" : "radio"
                          } },
                    "overNight" : { "@attributes" : { "title" : "One day Shipping ($20)",
                            "type" : "radio"
                          } }
                  }
                ]
            },
          "userInfo" : { "#text" : [ "\n      ",
                  "\n      ",
                  "\n      ",
                  "\n    "
                ],
              "@attributes" : { "title" : "User Information",
                  "type" : "FormBlock"
                },
              "Row" : [ { "#text" : [ "\n        ",
                        "\n      "
                      ],
                    "TextBox" : { "@attributes" : { "placeHolder" : "Select an username",
                            "title" : "Username",
                            "type" : "text"
                          } }
                  },
                  { "#text" : [ "\n        ",
                        "\n      "
                      ],
                    "TextBox" : { "@attributes" : { "placeHolder" : "Select a password",
                            "title" : "Password",
                            "type" : "password"
                          } }
                  },
                  { "#text" : [ "\n        ",
                        "\n      "
                      ],
                    "TextBox" : { "@attributes" : { "placeHolder" : "Eg: [email protected]",
                            "title" : "Email",
                            "type" : "text"
                          } }
                  }
                ]
            }
        }
    } }

To iterate this object I use a technique below.

function iterateJsonObj(obj) {
    for(key in obj) {
        if(!obj.hasOwnProperty(key) || key=="#text") {
            continue;
        }
        else if(obj[key]["@attributes"]!=null)
        {
            htmlStr += createHTMLStr(obj[key], key);
        }

        iterateJsonObj(obj[key]);
    }
}

Hope this question makes sense.

3
  • You really exceed the stack size with that tiny little object? Commented Mar 1, 2013 at 6:16
  • It was not that tiny, think an entire page, like entire gmail front end coming in as an object. :) Commented Mar 1, 2013 at 6:22
  • the issue could be with createHTMLStr... Commented Mar 1, 2013 at 7:21

1 Answer 1

2

Here is a degenerate repro case:

iterateJsonObj("Some text");

Can you see what's going on? The for loop apparently treats strings similarly to arrays of single-character substrings. "Shipping"[0] is "S" which is itself a string...

To fix this, I'd suggest testing that typeof obj[key] === "object" before iterating over it in this way.

Also, write unit tests. They will make your life easier. :)

Sign up to request clarification or add additional context in comments.

4 Comments

Hmm, now that you mention it, this does seem like an issue. Let me look into it, will update you. Thanks
+1 along with acceptance :) Also now I will write unit tests.
+1 I learnt something today... May I suggest obj===Object(obj) to test for objects? (takes care of the case of null).
obj===Object(obj) will return true for an array.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.