Rex Swain's Source Code:
CGI Environment Variable Demo

Copyright © 1996-1999 Rex Swain
Email rex@rexswain.com, Web http://www.rexswain.com
Permission granted to distribute unmodified copies
Reports of errors or omissions appreciated

File: environment.cgi

Last modified: 2 February 2006


#!/usr/bin/perl -w

# ENVIRONMENT.CGI
# Tell what we know about the CGI environment
# 18 Aug 1996  Rex Swain, Independent Consultant, rex@rexswain.com

# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #

# Define Globals

   $width = 45; 			       # for &wrap

# Start HTTP header

   print "Content-type: text/html; charset=iso-8859-1\n\n";

# Start HTML

   print "<HTML>
<HEAD>
<TITLE>Rex Swain's CGI Environment Variable Demo</TITLE>
</HEAD>";

   print '<BODY BGCOLOR="#FFFFFF" TEXT="#000000">';

   print '<!-- Google AdSense added 10/08/2003 -->
<TABLE ALIGN=right WIDTH=176 BORDER=0 CELLSPACING=0 CELLPADDING=0>
<TR>
 <TD WIDTH=16>&nbsp;</TD>
 <TD WIDTH=160>
 <script type="text/javascript"><!--
 google_ad_client = "pub-7510521706485409";
 google_ad_width = 160;
 google_ad_height = 600;
 google_ad_format = "160x600_as";
 google_color_border = "336699";
 google_color_bg = "FFFFFF";
 google_color_link = "0000FF";
 google_color_url = "008000";
 google_color_text = "000000";
//--></script>
<script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>
</TD></TR></TABLE>
';

   print "<CENTER>
<H1>Rex Swain's<BR>CGI Environment Variable Demo</H1>
Last updated 20 March 1997
<H4>Server: $ENV{'HTTP_HOST'}<BR>Perl: version $]</H4>
<A HREF=\"#get\">GET Demo</A>
&nbsp;&nbsp;
<A HREF=\"#post\">POST Demo</A>
&nbsp;&nbsp;
<A HREF=\"/cgi-bin/showsource.cgi?file=environment.cgi\">
Source Code</A>
</CENTER>
<P>
";

# CGI vars and descriptions

   undef %desc;
   $desc{'AUTH_TYPE'        } = 'Protocol-specific authentication method used to
				 validate the user.';
   $desc{'CONTENT_LENGTH'   } = 'Length of the data passed to the CGI program through
				 STDIN; implies REQUEST_METHOD is "POST".';
   $desc{'CONTENT_TYPE'     } = 'For queries which have attached information,
				 such as HTTP POST and PUT, this is the MIME content
				 type of the data.';
   $desc{'DOCUMENT_ROOT'    } = 'The directory from which web documents are served.';
   $desc{'GATEWAY_INTERFACE'} = 'CGI specification revision number to which server
				 complies.';
   $desc{'HTTP_ACCEPT'      } = 'List of the MIME types that the client can accept.';
   $desc{'HTTP_COOKIE'      } = 'Cookie values.
				 [See <A HREF="cookie.cgi">Cookie Demo</A>.]';
   $desc{'HTTP_FROM'        } = 'The Email address of the user making the request.
				 [Most browsers do not support this variable.]';
   $desc{'HTTP_REFERER'     } = 'The URL of the document that the client pointed to
				 before accessing the CGI program.';
   $desc{'HTTP_USER_AGENT'  } = 'The browser the client is using.';
   $desc{'PATH_INFO'        } = 'Extra path information, as given by the client.';
   $desc{'PATH_TRANSLATED'  } = 'Server-provided version of PATH_INFO
				 (with virtual-to-physical mapping).';
   $desc{'QUERY_STRING'     } = 'Query information passed to the program following URL
				 and "?"; implies REQUEST_METHOD is "GET".';
   $desc{'REMOTE_ADDR'      } = 'IP address of remote host making the request.';
   $desc{'REMOTE_HOST'      } = 'Remote hostname making the request.';
   $desc{'REMOTE_IDENT'     } = 'If the HTTP server supports RFC 931 identification,
				 then this variable will be set to the remote username
				 retrieved from the server. Usage of this variable
				 should be limited to logging only.';
   $desc{'REMOTE_USER'      } = 'Authenticated username (see AUTH_TYPE).';
   $desc{'REQUEST_METHOD'   } = 'The method with which the request was made
				 (e.g., "GET" or "POST" or "HEAD").';
   $desc{'SCRIPT_NAME'      } = 'Virtual path to the script being executed
				 (used for self-referencing URLs).';
   $desc{'SERVER_NAME'      } = 'Server host name, DNS alias, or IP address
				 (as it would appear in self-referencing URLs).';
   $desc{'SERVER_PORT'      } = 'Port number the request was sent to
				 (i.e., the host on which the server is running).';
   $desc{'SERVER_PROTOCOL'  } = 'Name and revision of the information protocol this
				 request came in with.';
   $desc{'SERVER_SOFTWARE'  } = 'Name and version of the server software
				 answering the request.';

# Add any other defined vars to %desc

   foreach (keys %ENV) {
      unless (exists $desc{$_}) {
	 $desc{$_} = '[unanticipated]';
      }
   }

# Print HTML TABLE

   print '<TABLE BORDER=4 CELLPADDING=4 CELLSPACING=0>
<TR ALIGN=left><TH ROWSPAN=2>Variable</TH><TH>Value</TH></TR>
<TR ALIGN=left><TH>Description</TH></TR>
';
   foreach (sort keys %desc) {
      print "<TR><TD ROWSPAN=2><TT>$_</TT></TD><TD>";
      if (exists $ENV{$_}) {
	 $v = $ENV{$_};
	 if ($v eq '') {
	    print '[defined but empty]';
	 }
	 else {
	    $v = &wrap($v,$width);
	    print "<TT>$v</TT>";
	 }
      }
      else {
	 print '[undefined]';
      }
      print "</TD></TR><TR><TD>$desc{$_}</TD></TR>\n";
   }
   print "</TABLE>\n";

# Demo GET

   print '<A NAME="get"><H3>GET</H3></A>';

   $me = '/cgi-bin/environment.cgi';
   $foo = $me . '?foo=1&amp;bar=2';
   print '<P>
One way to invoke a Perl program is with an HTML
<TT>&lt;A HREF=...&gt;</TT>...<TT>&lt;/A&gt; </TT>link.
Parameters are passed to Perl after the URL and a <TT>?</TT>.
Try it...
<P>
Hit me: <A HREF="' , $foo , '">' , $foo, '</A>
<P>
When this page reappears, you should see
<TT>REQUEST_METHOD</TT> of "<TT>GET</TT>".
The parameter names and values arrive via <TT>QUERY_STRING</TT>,
and should be "<TT>foo=1&amp;bar=2</TT>".
';

# Demo POST

   print '<A NAME="post"><H3>POST</H3></A>';

   print '<P>
Another way to invoke a Perl program is with an HTML
<TT>&lt;FORM METHOD=post&gt;</TT> tag, one or more
<TT>&lt;INPUT&gt;</TT> tags, and an
<TT>&lt;INPUT TYPE=submit&gt;</TT> tag.
Try it...
<P>
<FORM METHOD=post ACTION="' , $me , '">
 foo: <INPUT TYPE=text NAME=foo SIZE=3 VALUE=1>
 bar: <INPUT TYPE=text NAME=bar SIZE=3 VALUE=2>
 Hit me: <INPUT TYPE=submit>
</FORM>
<P>
When this page reappears, you should see
<TT>REQUEST_METHOD</TT> of "<TT>POST</TT>".
The parameter names and values arrive via STDIN,
and would be something like "<TT>foo=1&amp;bar=2</TT>".
<TT>CONTENT_LENGTH</TT> will be set to the length of that string.
<TT>CONTENT_TYPE</TT> will be something like
"<TT>application/x-www-form-urlencoded</TT>".
';

# See Also

   print '<HR SIZE=1 NOSHADE>
<H3>See Also</H3>
<UL>
<LI><A HREF="http://hoohoo.ncsa.uiuc.edu/cgi/">Common Gateway Interface</A>
documentation and examples (from NCSA)
<LI><A HREF="http://hoohoo.ncsa.uiuc.edu/cgi/env.html">CGI Environment Variables</A>
specification and examples (from NCSA)
</UL>
';

# Author

   print '<HR SIZE=1 NOSHADE>
<H3>Other Summaries and Demos</H3>
<UL>
<LI>See my <A HREF="http://www.rexswain.com/">home page</A> for other summaries and demos:
APL, REXX, XEDIT, Perl, HTML, RGB Colors, HTTP Cookies, Email Forms,
CGI Environment Variables, Server Side Includes, etc...
</UL>
';

   print '<CENTER>
<P><HR SIZE=1 NOSHADE></P>
<P>You are visitor
<IMG SRC="/cgi-bin/countrex.cgi?environment"
ALIGN=absmiddle WIDTH=90 HEIGHT=20 ALT="[Odometer]">
since 18 August 1996</P>
<HR SIZE=1 NOSHADE>
<P><FONT SIZE=-1>Copyright &copy; 1996-1997 Rex Swain<BR>
Email <A HREF="mailto:rex@rexswain.com">rex@rexswain.com</A>,
Web <A HREF="http://www.rexswain.com/">
http://www.rexswain.com/</A><BR>
Permission granted to distribute unmodified copies<BR>
Reports of errors or omissions appreciated</FONT></P>
</CENTER>
';

# End HTML

   print "</BODY>\n</HTML>\n";
   exit;

# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #

sub wrap {
   my ($txt,$width) = @_;
   my ($r, $tmp, $i, $j);
   $txt =~ s/&/&amp;/g;
   $txt =~ s/</&lt;/g;
   $txt =~ s/>/&gt;/g;
   $r = '';
   while (length($txt) > $width) {
      # do we have a space that browser will use to break within $width+1 chars?
      $tmp = substr($txt,0,$width+1);
      $i = 1 + rindex($tmp,' ');
      if ($i > 0) {
	 $r .= substr($txt,0,$i);
	 $txt = substr($txt,$i);
      }
      else {
	 # do we have a colon or slash within $width chars?
	 chop $tmp;			       # $tmp = substr($txt,0,$width);
	 $i = 1 + rindex($tmp,':');
	 $j = 1 + rindex($tmp,'/');
	 # use right-most colon or slash
	 if ($j > $i) { $i = $j; }
	 # else just break at $width
	 if ($i == 0) { $i = $width; }
	 $r .= substr($txt,0,$i) . '<BR>';
	 $txt = substr($txt,$i);
      }
   }
   $r .= $txt;
   return $r;
}