The theme function uses the func_get_args function. In php5 this gets the arguments by reference. In php4 this gets a copy of the arguments. So if I want to pass a variable by reference to a theme function and I'm using php4... I can't, because it gets a copy of the original variable.
e.g. calling theme('my_theme_func',$variable)
and defining function theme_my_theme_func(&$passed) {
will mean that changes which are made to $passed will affect $variable in php5 but won't in php4.
Not sure what the design is supposed to be. My guess is that you don't want to be able to alter original variables in theme functions. But it seems unsatisfactory that the functions behave differently in php4 and php5.
Comments
Comment #1
pwolanin commentedYes, I just stumbled upon the same behavior. I've been looking into the way the organic groups module themes nodes and have been perplexed by the fact that passing the node object by reference does not work as I expect.
This version works to modify the node body:
This version doesn't:
In the first case, passing in the pointer to $node is enough that all the contents of $node are present in theme_og_view() and can be modified and returned. It's very odd if different versions of PHP are so divergent. It should work. The webserver is running PHP Version 4.3.10.
Looking at the theme() function documentation: http://drupaldocs.org/api/head/function/theme
doesn't suggest anything to me.
Comment #2
pwolanin commentedsome comments about this issue are posted here:
http://us3.php.net/manual/en/function.func-get-arg.php
http://us3.php.net/manual/en/function.func-get-args.php
It also seems the same value/reference problem applies to call-user-func-array():
http://us3.php.net/manual/en/function.call-user-func-array.php
http://us3.php.net/manual/en/function.call-user-func.php
It seems there may be ways around this problem, though I haven't gotten anything to work yet. At the least, I'd think this should be mentioned in the theme() function documentation.
Comment #3
heine commentedI don't think theme functions should go about and modify the data that's passed to them. IMO they should only generate output.
Comment #4
Crell commentedAgreed. If your theme function needs to modify something, then you're doing something wrong. The only reason why you'd want to then would be for performance reasons if you're passing in a particularly large data structure. It's too bad PHP doesn't have a const keyword for such things. :-)
You are correct about there being by-ref issues in PHP 4's call_user_func() family of functions. That's not a Drupal issue, though, but a PHP 4 issue. The fix is to upgrade to PHP 5, where objects are always passed by reference, period. That's one of the reasons why PHP 5 does that.
Marking this by design, since Drupal is behaving exactly as a PHP app is expected to behave under PHP 4. That the rules changed for PHP 5 is PHP's problem, not Drupal's. :-)
Comment #5
pwolanin commentedI certainly agree that it's not a Drupal problem, except that the theme function documentation should mention it. I came across this when looking at a theme function in organic groups that is called under og_nodeapi (hook_nodeapi). The API for hook_nodeapi does specify passing by reference, and so I was trying to carry this pass-by-reference down to the function that actually made a change to the node.
Comment #6
Crell commentedIs this still an issue? Sounds like it's just a docs question at this point, if it's still an issue at all...
Comment #7
pwolanin commentedYes, this is really a documentation issue.
Comment #8
anschinsan commentedComment #9
drewish commentedwell 7.x is going going to be PHP5 only so if this needs to be fixed it needs to happen on the D6 side.
Comment #13
jhodgdonI don't see what needs to be documented really. theme() doesn't say anything about passing args by reference. Maybe it should be in the Handbook somewhere, but it can't be a very good practice to modify an object in a theme() function?