(jcwren) RE: Easy, elemental, but cool debug trick.
by jcwren (Prior) on May 25, 2000 at 00:06 UTC
|
I use a similiar technique. When debugging a CGI application, however, prints can really mess you up.
For that situation, I have a routine (below) that writes to a file. It accepts two parameters, one which is a class string, and a message string. The section string allows me to put messages in a arbitrary category (say, 'debug', 'authentication', or 'SQL'), and the text to be printed.
Each message is timestamped, and also stamped with a user ID (that's internal to me application, and could be ignored).
I also have a similiar version that use the syslog facility to write /var/log/messages.
sub debug_log
{
@_ == 2 or confess "Incorrect number of arguments";
my ($section, $action) = @_;
my $userid = 0;
my $string = 0;
$userid = $globalUserID || "<nobody>";
$string = sprintf ("%s %s %s:%s\n", scalar localtime, $userid, $sec
+tion, $action);
open (SINK, ">> /home/httpd/somedir/logfile") or confess "Can't ope
+n logfile";
print SINK $string;
close (SINK) or confess "Can't close logfile";
}
| [reply] [Watch: Dir/Any] [d/l] |
|
Just always use warn "foobar" if $DEBUG instead of print,
then it will do the right thingtm under both mod_cgi and
mod_perl.
For logging you should take a look at the Log::Agent module
available on CPAN.
| [reply] [Watch: Dir/Any] |
RE: Easy, elemental, but cool debug trick.
by KM (Priest) on May 24, 2000 at 21:23 UTC
|
I usually do what you showed above. Sometimes I do:
sub DEBUG () { 1 }
If I have many statements in there doing ... if $DEBUG.
I also use perl -c, the debugger, and whenever I am doing CGI I like to use CGI::Carp qw(fatalsToBrowser). I also use -T, but that isn't really a debugging thing.
Cheers,
KM | [reply] [Watch: Dir/Any] |
RE: Easy, elemental, but cool debug trick.
by Adam (Vicar) on May 24, 2000 at 21:30 UTC
|
Yeah, this is a good practice but adds an extra branch for every debug check. When I do this in C++ I use compiler directives to remove my debug code so that I don't bog down the final product. I wonder if Perl is smart enough to optimize out those branches when it compiles? This is more likely with KM's technique because Perl will inline the constant function. | [reply] [Watch: Dir/Any] |
|
Perl has a command-line flag, -P (capital P), which sends its input script
through the C pre-processor before perl compilation. I can't
recall ever hearing of anybody actually using it, though it's
obviously there for a reason, and this sounds like as
good a reason as any. (Note that
perldoc perlrun warns, 'Because both comments and
cpp directives begin with the # character, you should
avoid starting comments with any words recognized by
the C preprocessor such as "if", "else", or "define".'
Also note that you can't define values on the command line;
-D sets debugger flags.)
| [reply] [Watch: Dir/Any] |
Re: Easy, elemental, but cool debug trick.
by link (Novice) on May 28, 2000 at 18:14 UTC
|
Well, you might want to consider doing it with the constant
pragma.
use constant DEBUG => 1;
I tend to alternate between that and simply testing $^W:
print qq(\$foo is "$foo"\n) if $^W;
IMO, -w should never be enabled in production code (except
insofar as you think you might forget to reenable it when
you start development again!) so this works well. | [reply] [Watch: Dir/Any] [d/l] [select] |
|
2 comments. I use:
$debug = 20;
print "debug info here\n" if $debug > 5
print "even more info here\n" if $debug > 10
etc.
which lets me turn on and off levels of debug during
the process (e.g. subroutines can dump details or just
announce their presence as they get 'better' throughout
the scripting). I try to write these sorts of debug
stmts at the beginning and leave them in (often for
years ;-) as experience shows I'll need them later and
often need to turn them back on or bump the levels back
up as things change.
The other thing I just saw was somebody wrote all there
constant comparisons:
if ( 6 == $value ) { ...
claiming that this "catches" the missing "=" problem at
compile time (can't do 6 = $value) w/o the -w. Not sure
I believe its a good thing (ugly for one, reads wrong)
and not sure '6' shouldn't be $value_if_this sort of
constant somewhere (in most cases) but the fellow is
very accomplished programmer so take it for what you
will.
a
| [reply] [Watch: Dir/Any] |
RE: Easy, elemental, but cool debug trick.
by mattr (Curate) on Jun 11, 2000 at 15:05 UTC
|
I usually set $debug at top of a perl program or if
I am trying to make something useful, in a module which is
included by several. ($debug=$GlobalConfig::debug)
if ($debug>3) {print "Program Name: Error. $!";} ##DEBUG
I use 0=normal, 1..5 for more and more detail up to full
DBI negotiation, and unique negative number ranges for
debugging special cases.
This plus the block commenting code above seems useful.
The worst thing I've had is a client that actually sent me
back modified code (stripped out all my debugging and
copyright info, also renaming the files, since their server
couldn't handle something they had requested) and I had
to take Ediff to it. You'd think the perl interpreter would
not spend much time on testing the predefined constant..
You can also print to STDERR which you should be able to
catch live in another window by grep tail your.httpd.error.log
otherwise you'll need to turn on/off httpd header print
statements in your code to be able to catch early config
errors. Maybe better to look at that log agent module or
something spiffier for mod_perl segfault strangeness..
Best regards,
Matt | [reply] [Watch: Dir/Any] |
|
Oh forgot to say that the same client was saved by my
leaving the debugging statements intact, since after telling
them to change $debug I was able to debug it remotely through
my browser after they had installed it on their own server.
| [reply] [Watch: Dir/Any] |
RE: Easy, elemental, but cool debug trick.
by Bourgeois_Rage (Beadle) on May 25, 2000 at 23:00 UTC
|
Nice, I have similar techniques, but this one makes it real easy to clean up. I'll be sure to use this one. I think that if you write a short Perl program using REGEXP, you could scan through the document and remove all the lines with $DEBUG in it. That would seem to be the quickest way to clean up the file to me. | [reply] [Watch: Dir/Any] |
|
Neat idea, but why remove them? I amlost always need to turn
debugging back on sooner or later. How about something
like this:
perl -i.bak -e 's/^(.+\$DEBUG.+)$/#$1/' foo.pl
to turn DEBUG off and then
perl -i.bak -e 's/^#(.+\$DEBUG.+)$/$1/' foo.pl
to turn it back on.
At which point, do we even need to define a variable? As
a convention, any debug code would simply need #DEBUG hanging
off the end and simply change the \$DEBUG part of the regex
to look for #DEBUG.
Is it just me, or is there something very weird about using
perl to preprocess perl?
This waste of time has been gratefully brought to you by
mikfire
| [reply] [Watch: Dir/Any] [d/l] [select] |
|
This is very neat. Going one step further, to allow debug
blocks:
perl -pi.bak -e 's/^(.*)$/#$1/ if /\bDEBUG\b/../\bENDDEBUG\b/' foo.pl
to remove the block, and
perl -pi.bak -e 's/^#(.*)$/$1/ if /\bDEBUG\b/../\bENDDEBUG\b/' foo.pl
To reenable it. Then you can do something like this:
... code
# DEBUG
debug code
# ENDDEBUG
... more code
And yes, there is something very weird about using Perl to
pre-process Perl...
--ZZamboni
| [reply] [Watch: Dir/Any] [d/l] [select] |
|