Quoth Helmut Richter <
hh...@web.de>:
> I'd like to do a perl syntax check as distinct from an execution. I am
> well aware that there are many errors that cannot be found without
> execution but I'd like to first remove the errors that can be found
> without execution and *then* execute the script. My attempt was using the
> -wc flag, but this has no effect whatsoever.
It does. -c makes perl stop at the end of the main compile-time phase,
exactly at the point where it stops invoking CHECK blocks and starts
invoking INIT blocks.
> > perl -wc
ali.pl
> [Fri Jan 20 16:51:56 2012]
ali.pl: Variable "$body" is not imported at
>
ali.pl line 362.
> [Fri Jan 20 16:51:56 2012]
ali.pl: (Did you mean &body instead?)
<snip>
> Status: 500
> Content-type: text/html
<snip>
>
> The script is intended as CGI Script. The format of the error messages, to
> wit the same format as web server log entries and a status code 500, is
> hardly conceivable as pure syntax error messages from perl. Rather, the
> code must have been executed somehow. How could I prevent that?
'use' statements happen at compile time. (That's the point.) This means
that any code executed as part of a module's ->import method will be run
even under -c. Presumably you are using some module (CGI::Carp?) that
hooks into $SIG{__WARN__} (or something similar) and changes the warning
format: the only way to stop that code from running is to comment out
the 'use' statement.
As a matter of good style, modules shouldn't do anything 'important'
(open files, connect to databases, print output...) during compile time,
but should wait to be asked. Since this *is* just a matter of style,
though, there is nothing preventing modules from ignoring it if they
choose to. CGI::Carp is slightly bending the rules in the interest of
making debugging possible for people with no shell access.
As for preventing it: you can't. For one thing, 'strict' and 'warnings'
are switched on by explicit code in their ->import methods; if you could
somehow prevent execution of any Perl at all you would find strictures
were never switched on. For another, your code probably wouldn't even
compile, since it probably needs subs imported at compile time: and an
->import method can do anything it likes, you can't restrict it to just
exporting symbols and nothing else.
That said, you may be interested in Perl::Critic, which performs static
linting of Perl code (without executing anything ever). Personally I
find it inflexible and irritating (I won't use a spell-checker, either),
but a lot of people seem to find it useful. It's based on Adam Kennedy's
PPI, which spends a long time explaining exactly why it's impossible to
parse Perl statically and then goes on to make a best-effort attempt
anyway.
Ben