Early Bird Registration for DrupalCon Portland 2024 is open! Register by 23:59 PST on 31 March 2024, to get $100 off your ticket.
Currently drupal_to_js serializes all php arrays as JavaScript objects; this leads to unnecessary hand cramps when dealing with simple numeric arrays. The simplest thing to do is to detect if an array is associative (based on this: http://ca3.php.net/manual/en/function.is-array.php#41179 ) and then do the right thing:
function drupal_to_js($var) {
switch (gettype($var)) {
case 'boolean':
case 'integer':
case 'double':
return $var;
case 'resource':
case 'string':
return '"'. str_replace(array("\r", "\n"), array('\r', '\n'), addslashes($var)) .'"';
case 'array':
$output = array();
if(!(is_array($var) && array_keys($var)!==range(0,sizeof($var)-1))) {
foreach($var as $v) {
$output[] = drupal_to_js($v);
}
return '[ ' . implode(', ', $output)." ]";
}
case 'object':
$output = array();
foreach ($var as $k => $v) {
$output[] = $k .': '. drupal_to_js($v);
}
return '{ '. implode(', ', $output) .' }';
default:
return 'null';
}
}
simple tests for this:
$data1 = array('x', 'y');
$data2 = array('x'=>array('x'=>'y', 'q'), 'y'=>1234);
$data3 = array($data1, array('x'=>'y','foo'=>1));
$data4 = array(4=>'x', 2=>'y');
echo "data1: ".drupal_to_js($data1)."\n";
echo "data2: ".drupal_to_js($data2)."\n";
echo "data3: ".drupal_to_js($data3)."\n";
echo "data4: ".drupal_to_js($data4)."\n";
expected output:
data1: [ "x", "y" ]
data2: { x: { x: "y", 0: "q" }, y: 1234 }
data3: [ [ "x", "y" ], { x: "y", foo: 1 } ]
data4: { 4: "x", 2: "y" }
Note: this also places drupal_to_js closer in functionality to PHP-JSON ( http://www.aurore.net/projects/php-json/ ), so if you have this extension compiled in you can do fancy things like this:
function _json_encode($data){
if(is_callable('json_encode')) {
return json_encode($data);
} else {
return drupal_to_js($data);
}
}
Comment | File | Size | Author |
---|---|---|---|
#1 | php_is_array.patch | 830 bytes | greggles |
arrayfix.patch | 269 bytes | anisotropic | |
Comments
Comment #1
gregglesI created a patch based upon anisotropic's code in this block. I then created a test site using this and nothing blew up, but I'm not sure what a good test for this particular code would be so I can't really claim it's been 'tested'. I just wanted to move it to "patched, code needs review" stage and make it easier for others to test out.
I created the patch against a cvs checkout current as of this comment. I'm also changing the version since his description of the code is still accurate against that cvs version.
Comment #2
gregglesI didn't even notice that it already had a patch...
I guess the status deserved to be changed already.
I still have some value added: the later patch is in the Drupal standard patch format.
Comment #3
Thox CreditAttribution: Thox commentedI don't know about this particular method for checking the type of array, but in essence I agree that it should be done. If nothing else, it requires a comment to explain what is going on.
Comment #4
Steven CreditAttribution: Steven commentedCode style is bad. And the switch fallthrough should be indicated with a comment.
Comment #5
Steven CreditAttribution: Steven commentedI committed a modified version of this patch as part of 47510. The is_array() check in the above code is redundant.
Comment #6
(not verified) CreditAttribution: commented