Difference between revisions of "CGI (perl)"
Line 35: | Line 35: | ||
=Typical Flow= | =Typical Flow= | ||
− | print $cgi->header; | + | # Setting cookies |
+ | my $cookie1 = $cgi->cookie(-name=>'sessionID',-value=>'m0m0',-expires=>'+30m'); | ||
+ | my $cookie2 = $cgi->cookie(-name=>'user',-value=>'Jimmy'); | ||
+ | |||
+ | print $cgi->header(-cookie=>[$cookie1,$cookie2]); | ||
# CGI.pm can generate its own HTML. Do we need it? No. | # CGI.pm can generate its own HTML. Do we need it? No. | ||
Line 56: | Line 60: | ||
# Set -override=>1 to always use -value. | # Set -override=>1 to always use -value. | ||
+ | print $cgi->hidden('hidden1','value'); | ||
+ | print $cgi->hidden(-name=>'hidden2',-default=>[qw/alpha beta gamma/]); | ||
+ | # Retrieve multi-valued fields in list context. | ||
+ | |||
print $cgi->textfield('field1','A default value',50,80); | print $cgi->textfield('field1','A default value',50,80); | ||
# -name, -value, -size, -maxlength | # -name, -value, -size, -maxlength | ||
Line 62: | Line 70: | ||
print $cgi->password_field('pass1','a pass!',50,80); | print $cgi->password_field('pass1','a pass!',50,80); | ||
# Same as textfield | # Same as textfield | ||
+ | |||
# Dropdown lists: Tricky! | # Dropdown lists: Tricky! | ||
Line 75: | Line 84: | ||
}; | }; | ||
print $cgi->popup_menu('menu1',[qw/red green blue/],'red',$labels,$attributes); | print $cgi->popup_menu('menu1',[qw/red green blue/],'red',$labels,$attributes); | ||
− | # -name, -values, - | + | # -name, -values, -default, -labels, -attributes |
# -attributes sets plain HTML attributes, hence the outrageous syntax! | # -attributes sets plain HTML attributes, hence the outrageous syntax! | ||
+ | |||
# Nested dropdown lists: Trickier! | # Nested dropdown lists: Trickier! | ||
Line 109: | Line 119: | ||
+ | # Scrolling lists | ||
+ | print $cgi->scrolling_list(-name => 'list1', | ||
+ | -values => [ | ||
+ | 'red', | ||
+ | 'green', | ||
+ | 'blue', | ||
+ | ], | ||
+ | -labels => $labels2, | ||
+ | -attributes => $attributes2, | ||
+ | -default => 'red', | ||
+ | -size => 2, | ||
+ | -multiple => 1); | ||
+ | # Note: It appears -default must be used instead of -value here. | ||
+ | # -default may be a list ref if -multiple is true. | ||
+ | |||
+ | |||
+ | # Checkbox groups | ||
+ | my @group1 = $cgi->checkbox_group(-name => 'group1', | ||
+ | -values => [qw/red blue green/], | ||
+ | -default => [qw/red green/], | ||
+ | -labels => $labels2 | ||
+ | ); | ||
+ | print "<div>$_</div>" foreach @group1; | ||
+ | # The return param is an array of the checked values. | ||
+ | # Note: -attributes is available here, but it only styles the | ||
+ | # checkbox itself--not the label--so it's pretty worthless. | ||
+ | |||
+ | |||
+ | # Single checkboxes | ||
+ | print $cgi->checkbox(-name=>'check1', | ||
+ | -checked=>1, | ||
+ | -value=>'A ludicrous string', | ||
+ | -label=>'Isolated Decision' | ||
+ | ); | ||
+ | # The return param is -value if checked, undef else. | ||
+ | # -class only applies to the checkbox. | ||
+ | |||
+ | |||
+ | # Radio buttons | ||
+ | my @radios = $cgi->radio_group(-name => 'radio1', | ||
+ | -values => [qw/red blue green/], | ||
+ | -default => 'green', | ||
+ | -labels => $labels2 | ||
+ | ); | ||
+ | print "<div>$_</div>" foreach @radios; | ||
+ | # Again, -attributes is worthless. | ||
+ | |||
+ | |||
print $cgi->filefield('upload1','',50,80) | print $cgi->filefield('upload1','',50,80) | ||
# -name, -default, -size, -maxlength | # -name, -default, -size, -maxlength | ||
# -default is typically ignored. | # -default is typically ignored. | ||
# DISABLE_UPLOADS must be false, form encoding must be $cgi->MULTIPART. | # DISABLE_UPLOADS must be false, form encoding must be $cgi->MULTIPART. | ||
− | + | ||
− | + | ||
− | |||
# Uploaded files are stuffed somewhere. upload() returns the filehandle | # Uploaded files are stuffed somewhere. upload() returns the filehandle | ||
# of the file uploaded with the given parameter name, or undef if there | # of the file uploaded with the given parameter name, or undef if there | ||
Line 131: | Line 188: | ||
# suitable for setting -status in header() | # suitable for setting -status in header() | ||
} | } | ||
+ | |||
+ | |||
+ | # Submit buttons | ||
+ | print $cgi->submit('submit1','Send'); | ||
+ | # -name, -value | ||
+ | # Submitting with this button is var submit1=Send. | ||
+ | # More than one submit is allowed. | ||
+ | |||
+ | # Reset buttons... useless. Forget them. | ||
+ | |||
+ | # Image buttons | ||
+ | print $cgi->image_button(-name=>'image1', | ||
+ | -src=>'button.png', | ||
+ | -alt=>'Alternate text'); | ||
+ | # The button submits; it returns the coordinates of | ||
+ | # the click as parameters 'image1.x' and 'image1.y'. | ||
=Redirects= | =Redirects= |
Revision as of 04:46, 12 April 2005
Use
When using CGI on its own, don't be satisfied with the normal use
. Prefer this:
use CGI 3.00; $CGI::DISABLE_UPLOADS = 1; $CGI::POST_MAX = 512 * 1024;
Version 3.00 introduced (as on 2005 April 12) the most recent XSS vulnerability fix.
$CGI::DISABLE_UPLOADS should be set high unless the script is intended to accept uploaded files.
$CGI::POST_MAX is the largest acceptable POST, in bytes.
Xana::CGI subclasses CGI::Safe, which sets the two variables already, and messes with %PATH for security. CGI::Safe itself is also pretty simple, if available (if it isn't, it's pure Perl so a compiler is not necessary to install).
use CGI::Safe 'taint';
Xana::CGI uses CGI::Safe with 'taint' already.
use Xana::CGI;
Instantiation
Using CGI:
my $cgi = new CGI;
Using CGI::Safe:
my $cgi = CGI::Safe->new( DISABLE_UPLOADS => 0, POST_MAX => 1024 * 1024 );
Those arguments are optional. Xana::CGI is-a CGI::Safe.
Typical Flow
# Setting cookies my $cookie1 = $cgi->cookie(-name=>'sessionID',-value=>'m0m0',-expires=>'+30m'); my $cookie2 = $cgi->cookie(-name=>'user',-value=>'Jimmy'); print $cgi->header(-cookie=>[$cookie1,$cookie2]); # CGI.pm can generate its own HTML. Do we need it? No. print <<EOF ; <html> <head> <title>Some title</title> </head> <body> EOF print $cgi->start_form; # -method=>'POST', -action=>this script, -enctype=>'application/x-www-form-urlencoded' # -enctype may be multipart/form-data. # Set like -enctype => $cgi->URL_ENCODED (or $cgi->MULTIPART) # -name and -onSubmit can be used with scripts. # Abort submission by returning false from onSubmit. # Previous value in fields in maintained across requests. # Set -override=>1 to always use -value. print $cgi->hidden('hidden1','value'); print $cgi->hidden(-name=>'hidden2',-default=>[qw/alpha beta gamma/]); # Retrieve multi-valued fields in list context.
print $cgi->textfield('field1','A default value',50,80); # -name, -value, -size, -maxlength print $cgi->textarea('field2','A long default value',80,25); # -name, -value, -rows, -columns print $cgi->password_field('pass1','a pass!',50,80); # Same as textfield # Dropdown lists: Tricky! my $labels = { red => 'The color red', green => 'The color green', blue => 'The color blue' }; my $attributes = { red => { class => 'redStyle' }, green => { class => 'greenStyle' }, blue => { class => 'blueStyle' } }; print $cgi->popup_menu('menu1',[qw/red green blue/],'red',$labels,$attributes); # -name, -values, -default, -labels, -attributes # -attributes sets plain HTML attributes, hence the outrageous syntax! # Nested dropdown lists: Trickier! my $labels2 = {}; my $attributes2 = {}; for(qw/red green blue silver lime/) { $labels2->{$_} = "The color $_"; $attributes2->{$_} = { class => $_ . 'Style' }; } print $cgi->popup_menu(-name => 'menu2', -values => [ 'red', 'green', 'blue', $cgi->optgroup(-name => 'Stranger colors', -values => ['silver','lime'], -labels => $labels2, -attributes => $attributes2) ], -labels => $labels2, -attributes => $attributes2); # The list ends up looking like this: # The color red # The color green # The color blue # *Stranger colors* # The color silver # The color lime # An option selected from the submenu is returned as the # value of 'menu2'. Note also that the submenu heading # may also be classed by setting -class in optgroup(). # Scrolling lists print $cgi->scrolling_list(-name => 'list1', -values => [ 'red', 'green', 'blue', ], -labels => $labels2, -attributes => $attributes2, -default => 'red', -size => 2, -multiple => 1); # Note: It appears -default must be used instead of -value here. # -default may be a list ref if -multiple is true. # Checkbox groups my @group1 = $cgi->checkbox_group(-name => 'group1', -values => [qw/red blue green/], -default => [qw/red green/], -labels => $labels2 );
print "
" foreach @group1;
# The return param is an array of the checked values. # Note: -attributes is available here, but it only styles the # checkbox itself--not the label--so it's pretty worthless. # Single checkboxes print $cgi->checkbox(-name=>'check1', -checked=>1, -value=>'A ludicrous string', -label=>'Isolated Decision' ); # The return param is -value if checked, undef else. # -class only applies to the checkbox. # Radio buttons my @radios = $cgi->radio_group(-name => 'radio1', -values => [qw/red blue green/], -default => 'green', -labels => $labels2 );
print "
" foreach @radios;
# Again, -attributes is worthless. print $cgi->filefield('upload1',,50,80) # -name, -default, -size, -maxlength # -default is typically ignored. # DISABLE_UPLOADS must be false, form encoding must be $cgi->MULTIPART. # Uploaded files are stuffed somewhere. upload() returns the filehandle # of the file uploaded with the given parameter name, or undef if there # wasn't one. my $upload1 = $cgi->upload('upload1'); if(defined $upload1) { # ... Use $upload1 as a filehandle ... open(OUTFILE,">>/dev/null") or die; my $buffer; while(my $read=read($upload1,$buffer,1024) { print OUTFILE $buffer; } } elsif($cgi->cgi_error) { # The HTTP error status 400 Bad Request is returned, # suitable for setting -status in header() } # Submit buttons print $cgi->submit('submit1','Send'); # -name, -value # Submitting with this button is var submit1=Send. # More than one submit is allowed. # Reset buttons... useless. Forget them. # Image buttons print $cgi->image_button(-name=>'image1', -src=>'button.png', -alt=>'Alternate text'); # The button submits; it returns the coordinates of # the click as parameters 'image1.x' and 'image1.y'.
Redirects
These statements generate entire headers. Don't print a $cgi->header
as well.
# Generic 302 print $cgi->redirect('http://example.com/');
# 301: Moved Permanently # 302: Found # 303: See Other print $cgi->redirect(-uri => 'http://example.com/', -status => 301);
Forms
See also Forms (CPAN).
print $cgi->start_form; print $cgi->end_form;