简体   繁体   中英

JSON parse unexpected non-whitespace character

Currently got the following variable

"{"error":"Wrong account"}"

And Im parsing it like this

var message = JSON.parse(event.data);
console.log(message['error'])

The console.log works but Im getting this error

SyntaxError: JSON.parse: unexpected character at line 1 column 1 of the JSON data

I think the json format is correct (made using php json_encode) so I dont really know wheres the error

So after some debugging (see below in reverse for that chain) it turns out the issue is another message which isn't JSON encoded is being caught by the related code first.

While we could trace through to where the other message is coming from (on further discussion, there is apparently a handshake that was being sent on the same socket and getting picked up by this handler—the culprit at last!), it might be easier to just drop it, so we need some validation code:

Credit to an amalgam of the answers by @Gumbo and @Matt for the following (because we need to actually run a test, but want to check for null/etc cases too so we're not throwing errors when we go to reference the return object)

function IsValidJSON(test) {
    try {
        var obj = JSON.parse(test);
        if (obj && typeof obj === "object" && obj !== null) {
            return true;
        }
    } catch (e) {

    }
    return false;
}

With that function available, now we can simply change the original code to:

var message;
if (IsValidJSON(event.data)) {
    message = JSON.parse(event.data);
    console.log(message['error']);
}

I'm leaving the following earlier versions of the answer in as a debug trail, since this ended up being more of a process of finding the problem than one where the problem and solution were self evident:


So this has turned slightly mysterious, let's try going back to basics and verifying that nothing weird/unprintable is in the output:

var asciioutput = event.data.charAt(0) + ':' + event.data.charCodeAt(0);

for (var i = 1; i < event.data.length; i++) {
    asciioutput += ', ' + event.data.charAt(i) + ':' + event.data.charCodeAt(i);
}

console.log(asciioutput);

You should end up with a result in your console that looks like this:

{:123, ":34, e:101, r:114, r:114, o:111, r:114, ":34, ::58, ":34, W:87, r:114, o:111, n:110, g:103,  :32, a:97, c:99, c:99, o:111, u:117, n:110, t:116, ":34, }:125

If your variable includes those wrapping quotes, then they are the problem: remove them.

In other words, if console.log(event.data) shows, literally "{"error":"Wrong account"}" then you need to strip the wrapping quotes such that the variable becomes {"error":"Wrong account"} before you try parsing it into JSON.

For example:

var message;
if (event.data.slice(0,1) == '"') {
message = JSON.parse(event.data.slice(1,-1));
} else {
message = JSON.parse(event.data);
}

(see jsfiddle for a working example—note the name change)

(note that this example entirely assumes that if there is a starting quote, there is also an end quote: you might want to build out more logic if that's not consistently true)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM