Passing javascript function to JSON

I am trying to implement jQCloud word cloud with a click event handler. I need to pass a javascript function in JSON.

In C # I made dynamic JSON text

foreach (var r in result)
{
    sbChart.Append("{\"text\": \"" + r.Key + "\", \"weight\": " + r.Count().ToString() + ", ");
    sbChart.Append("\"handlers\": { \"click\": \"function() { alert('You clicked " + r.Key + "');}\"}}, ");
}
if (sbChart.Length != 0)
{
    returnString = "[" + sbChart.ToString().Substring(0, sbChart.Length - 2) + "]";
}

      

I am returning this via a web method in javascript where my code is

var words = JSON.parse(strJSON);
$('#div').jQCloud(words);

      

The generated JSON is -

[
  {"text": "the", "weight": 111, "handlers": { "click": "function() { alert('You clicked the');}"}}, 
  {"text": "in", "weight": 66, "handlers": { "click": "function() { alert('You clicked in');}"}}
]

      

However, since my function is a string, it does not execute as an object. And if I remove the double quotes before and after the function statement, it gives me an error Invalid Character

during parsing.

Please help me how can I make this warning?

+3


source to share


3 answers


Thanks a lot for your suggestions above. But I got a response from how to provide a click handler in JQCloud

I modified it a bit according to my requirement and it worked



var tag_list = new Array();
    var obj = GetCustomJsonObj(strJSON);
    for (var i = 0; i < obj.length; i++) {
        tag_list.push({
            text: obj[i].text,
            weight: obj[i].weight,
            //link: obj[i].link,
            handlers: {
                click: function () {
                    var zz = obj[i];
                    return function () {
                        alert("you have clicked " + zz.text);
                    }
                }()
            }
        });
    }

      

+1


source


If you absolutely need to pass a function to your page in this way (see below, but below), you can use for it eval

, since you are the one who will have the text eval

that has no security issue (and the speed issue is not an issue and lasted for years). I'm not sure what you want to do with the function, but for example:

$(".foo").on("click", eval(words[0].handlers.click));

      

... will validate the function and assign the result as a click handler for elements matching the selector .foo

.

But , it's almost certainly the best way to structure things. Instead of passing functions in JSON, you can use these functions in your JavaScript already on some map:



var clickHandlers = {
    "the": function() { alert("You clicked the"); },
    "in": function() { alert("You clicked the"); }
};

      

... and then just enter the key ( "the"

, "in"

) in your JSON.

Or, given that they are the same as what was clicked, figure out what was clicked ("or" in) from the item that was clicked.

Or any of a dozen other things, but what they have in common is that the functions are defined in your JavaScript code, not sent back via JSON, and then you wire those functions using the information in JSON, not with actual functions in JSON.

+2


source


Functions should not be passed as JSON, and this is a rather large security issue for executing arbitrary logic passed by a data call. That being said eval

, use to fix the problem.

Something like

var action = eval(response[0].handlers.click); // evaluates the string as javascript, and returns the value, in this case a function.

action();

      

+1


source







All Articles