3

I often use print_r($value, true) to dump some variables in log statements, and sometimes I forget to set the second parameter to true, which then might result in instead of the result being in the log statement, in most cases it just gets lost, but sometimes it is even rendered to the users browser.

This just happened to me, and within the object graph where some credentials, and other things that you normally would not like the end user to see. The problem was that instead of passing true as the second parameter, for some reason I passed null 1 year ago. And now there was some system failure that made the wrong output show.

What do you do to avoid having stacktraces output by programmer error? Why do all PHP dumping functions just echo the output by default? Searching though our codebase, I found quite a lot of invocations of print_r without the second parameter set to true.

I also use json_encode() for debug output sometimes, because the output is sometimes more concise and friendly to read. Any drawbacks with that approach?

We normally use some sort of output buffering, but not everywhere.

Mouna Cheikhna
  • 38,870
  • 10
  • 48
  • 69
Paul Weber
  • 6,518
  • 3
  • 43
  • 52
  • Either be more careful with `print_r()` or write some kind of wrapper function for `print_r()` that never echoes. ;) – WWW Feb 08 '12 at 21:40
  • @Paul, You can [redefine `print_r` and `var_export`](http://stackoverflow.com/a/2640992/632951) to make it spit to error log regardless of the second argument. – Pacerier Mar 25 '15 at 15:04

5 Answers5

4

var_export() returns a string if the second argument is true; but it's up to you to remember to set that second argument

Mark Baker
  • 209,507
  • 32
  • 346
  • 385
3

Why not create a custom function that will wrap all your print_r calls? I use something like this:

function good_print() {
    $log = '';
    foreach(func_get_args() as $arg) $log .= print_r($arg, true);
    return $log;
}

It saves time, gives me better functionality, plus I don't have to worry about "did I use the right call this time?"

davethegr8
  • 11,323
  • 5
  • 36
  • 61
  • Yep, thats what we did. We already used a debug function (a wrapper for Zend_Log), and now we modified the parameter from a string to multiple parameters, that are then concatenated and dumped correctly ( boolean as true, false, null as null, structures as print_r ). This was inspired by javascripts console.log function. – Paul Weber Feb 10 '12 at 20:46
  • Nice, that sounds like a solid solution – davethegr8 Feb 11 '12 at 00:10
2

What do you do to avoid having stacktraces output by programmer error?

Simple, non production code is not allowed on production (var_dump, print_r, et al. are never useful in production). Enforce by in order of preference either build / testing system, source control, enforcing using only wrapper functions which can easily be disabled centrally, or if you really must, production server configuration.

Why do all PHP dumping functions just echo the output by default?

Because it's easiest during development.

Searching though our codebase, I found quite a lot of invocations of print_r without the second parameter set to true

And you also found a lot of or die('some errormessage); statements, also not a good idea in production for obvious reasons. Manual code is illustration, never production code, but alas treated as such by many a programmer.

I also use json_encode() for debug output sometimes, because the output is sometimes more concise and friendly to read. Any drawbacks with that approach?

Some extra load maybe, and no clear indicator it is for debugging (as mentioned earlier, var_dump is a red flag, json_encode isn't).

We normally use some sort of output buffering, but not everywhere.

I only use it when strictly needed, so, almost nowhere.

Wrikken
  • 69,272
  • 8
  • 97
  • 136
  • +1 for *" Enforce by ... build / testing system, source control"* –  Feb 08 '12 at 21:56
  • Well, what I have forgotten to mention is that the "evil" print_r invocation was in a legal logging statement, so we know what the invalid value was. – Paul Weber Feb 10 '12 at 20:58
1

As per the PHP manual docs on print_rdocs, you can tell print_r to return the results instead of outputting them with the second, optional bool parameter:

$test = array('var1', 'var2');
$val = print_r($test, TRUE); // won't output anything
echo $val; // output the normal print_r goodness you know and love

UPDATE

After actually reading the question I would suggest @davethegr8's solution, so you and others should probably vote for that over this answer. Another implementation:

function _print_r($val, $return=TRUE)
{
  print_r($val, $return);
}

Finally, a funny thing happens when you use test-driven development: You don't litter your source code with test debug statements because you've already handled it in your unit tests:

  • "and sometimes I forget to set the second parameter to true" – davethegr8 Feb 08 '12 at 21:41
  • Hmm, when I read your actual question and not just the title it seems you knew this. I'm with @Crontab -- you need to be careful about leaving `print_r` haphazardly lying around in your code. –  Feb 08 '12 at 21:43
0

What do you do to avoid having stacktraces output by programmer error?

You can set a custom method that prints errors only if the DEBUG option is set.

define('DEBUG', "DEBUG"); 

function print_log($input) {
    if (defined("DEBUG")) {
        print_r($input, true);
    }
}

and instead of calling print_r just call print_log.

You may also want to take a look at Krumo, which is an amazing replacement for var_dump and print_r for displaying PHP variables in a structured way.

TRiG
  • 10,148
  • 7
  • 57
  • 107
Mouna Cheikhna
  • 38,870
  • 10
  • 48
  • 69