Question

I have an invalid Json string that I need to parse to an object and feed to a viewmodel:

var s = "{ a: new Date(1400000000000) }"; // from a server, can't change this
eval("var b = " + s);                     // parse it to a var b
var vm = new viewmodel(b);                // pass var b to the viewmodel

This works, but I end up with an intermediate object b before I can use the parsed object

So I tried:

var s = "{ a: new Date(1400000000000) }"; // from a server, can't change this
var vm = new viewmodel(eval(s));          // parse the object and pass to viewmodel

but that doesn't work

Can you explain why?

Is there another way to do this without the need for an intermediate var b?

Was it helpful?

Solution 2

You need to wrap the object expression (it's not a valid statement alone):

var s = "{ a: 3, b: 7 }";
var obj = eval('(' + s + ')');

Needless to say that eval is not secure, but if you have no choice... Just be aware that this will execute any code the server sends to you. c.f. Why is using the JavaScript eval function a bad idea? for a more thorough discussion on the matter


Extra fun: try entering both { a: 3, b: 7 } and ({ a: 3, b: 7 }) in the online esprima parser :) http://esprima.org/demo/parse.html

OTHER TIPS

Try to use in this way

var vm = new viewmodel(eval('(' + s + ')')); 

Another way to do this is:

var s = "{ a: new Date(1400000000000) }";
var vm = new viewmodel(new Function('return ' + s).call());  

The difference between using eval is that this way the code (s) cannot access local variables because the code runs in a separate function scope.

The best way to parse JSON is to use JSON.parse(). eval() is not very secure.

var vm = new viewmodel(JSON.parse(s));
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top