13.6. Heading Off Errors

The output of your program is usually parsed through the Web server (unless you use the increasingly rare nph feature), which adds headers like a status line (unless you provide one yourself), a server identification line, and a date. The essential header for you to remember is Content-type: you must output this one.

(Weeell … the complete truth is more complicated, but of little use. You can output any number of lines that look like headers [any line containing a colon with at least one nonspace character on either side, based on experimentation], and these lines are faithfully passed on by the server as though they actually mean something. As long as you output a blank line before your content, it'll make it through; if you don't output a Content-type header, some servers will put one on for you [set to text/plain]; some browsers interpret the absence of a Content-type header to mean it is of type text/html. This is of academic interest at best.)

The bottom line is that the first output from your program must be header lines including a Content-type header, which must be followed by a blank line before your content. If you use CGI.pm, the header routine is all you need to output headers properly; as long as you call it before anything else that produces output, you should have little to worry about. But sometimes, the bugs can gang up on you and foil this strategy.

Run your CGI program from the command line to check that it produces the right output in the right order.


It is crucial to find out what your program outputs to STDERR. This is where the output from die and warn goes, including any complaints from use strict or -w. The popular Apache server puts STDERR messages in the error log file, but the Netscape Enterprise server directs them to the browser in the order it receives them. What will that be? Let's look at a simple script that produces a warning in addition to output:

#!/usr/bin/perl -w
use strict;
my $x;
print "Content-type: text/plain

";
print "Value of $x is $x
";

Run this at the shell prompt and you'll see

Content-type: text/html

Use of uninitialized value in concatenation (.) at foo.cgi line 5.
Value of $x is

But that's not the order the output goes to the Web server! Because we're outputting to the terminal, STDOUT is by default line buffered, which means that its output is flushed on every newline. However, if output is not going to the terminal, STDOUT is fully buffered (unless the Web server decides otherwise), and won't come out until after the output to STDERR.

Upshot: try this on a server that sends STDERR to the browser as well, and you'll get a 500 Server Error. As far as the server was concerned, you sent

Use of uninitialized value in concatenation (.) at foo.cgi line 5.
Content-type: text/html

Value of $x is

The first line does not look like a header.

Whew! Is this a lot to remember or what? That's why we reiterate: Test your program from the command line first and follow Perl of Wisdom #17—Eliminate all warnings before proceeding with development. In addition, add the line

$| = 1;

near the beginning of your program to unbuffer STDOUT so that when you send output, it gets passed to the Web server immediately.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset