1

Is there a way to parse NON wellformed JSON, other than using eval?

The background is, that I'm using data tag values to draw a graph like this:

<div id="data" data-idata="[1,2,3]" data-sdata="['foo','bar','baz']"></div>

This works flawlessly with numeric values, these values are delivered as an array directly in jQuery data, no need to parse JSON here.

However, for the labels a string array is to be passed. eval can parse the string in sdata just fine, but JSON.parse and jQuery.parseJSON fail, because it's not wellformed JSON.

var $data = $("#data").data(),
    values;

// use eval
out("#out", eval($data.sdata)); // works...

// use JSON.parse
try
{
    values = JSON.parse($data.sdata);
} catch(e) {
    // silent catch
}
out("#out1", values); // values is undefined

I put together a JsFiddle here to check the thing.

gpinkas
  • 2,291
  • 2
  • 33
  • 49

4 Answers4

3

You get error because ['foo','bar','baz'] contains single-quotation marks. JSON RFC specifies that string should be enclosed in double-quotation marks.

There could be a few work-arounds.

Switch quotation marks in the data- attributes:

<tag data-sdata='["foo","bar","baz"]' />

Or replace in Javascript:

values = JSON.parse($data.sdata.replace("'","\""));
Kita
  • 2,604
  • 19
  • 25
1

You don't need to parse. Simply use .data(), the function does it for you.

I have changed your HTML, I have swapped quotes in line data-sdata="['foo', 'bar', 'baz']" as JSON should use in double-quotation(") marks.

HTML

<div id="data" data-idata="[1,2,3]" data-sdata='["foo", "bar", "baz"]'></div>

Script

out("#out1", $("#data").data('idata'));
out("#out2", $("#data").data('sdata'));

DEMO

Satpal
  • 132,252
  • 13
  • 159
  • 168
0

Ofcourse you cannot easy parse corrupted data for 100% this goes for any data-formats and not only JSON.

If the reason the data are malformed are always the same you should fix it with some str_find and replacement functions.

If it is irregular you have no real chance except writing a really intelligenz and big algorithm. The best way here would be to try to extract the real raw data out of the corrupted string and build a real JSON string with valid syntax.

Steini
  • 2,753
  • 15
  • 24
0

Try

html

<div id="data" data-idata="[1,2,3]" data-sdata='["foo","bar","baz"]'></div>
<div id="out1">out1</div>
<div id="out2">out2</div>

js

$(function () {
    var out = function (outputId, elem, dataId) {
        return $.each(JSON.parse($(elem).get(0).dataset["" + dataId])
          , function (index, value) {
            $("<ul>").html("<li>" + index + " -> " + value + "</li>")
              .appendTo(outputId);
        });
    };
    out("#out1", "#data", "idata");
    out("#out2", "#data", "sdata");
});

jsfiddle http://jsfiddle.net/guest271314/4mJBp/

guest271314
  • 1
  • 15
  • 104
  • 177