I am sure that this is a FAQ, but I had a very hard time finding
examples of code for doing file upload. I wanted to post this here in
order to have it in the permanent record so that other folks don't have
to spend days figuring this out.

I have a generic form method which looks like:


sub form {
    use Apache::Request;
    my $r = Apache->request();
    my $apr = Apache::Request->new($r);
    my @keys = $apr->param;

    my %form;
    foreach my $key(@keys) {

        my @value = $apr->param($key);
        next unless scalar @value;

        if ( @value > 1 ) {
            $form{$key} = \@value;
          } else {
            $form{$key} = $value[0];
        }
    }

    my $upload = $apr->upload;
    if ($upload) {
        $form{UPLOAD} = $upload;
    }

   return \%form;
}

And the explanation is thus. This function returns a hashref. The keys
of the hash are the names in your form. The values in the hash are the
values entered in those fields, with the exception that a multiple
select list with multiple things selected will return a listref. This is
the way that CGI_Lite, for example, handles things, and that is what I
was trying to be compatible with for my own legacy code. You can of
course change that if you have different conventions.

*If* your form contained a file upload element, (Don't forget to make
your form encoding="multiplar/form-data"  I always forget that.)
then $form{UPLOAD} will contain a file upload object, which you can
make calls back into.

For example:

my $form = Your::Class::form(); # Wherever you put this function
if (my $file = $form->{UPLOAD}) {
    my $filename = $file->filename; # If you need the name

    # And, if you want to save the file at $filelocation ...
    open F, ">$filelocation";
    my $filehandle = $file->fh;
    while (my $d = <$filehandle>) {
        print F $d;
    }
    close F;
}

That should give you the general idea of how this works. This lets you
have a generic form handler that does "normal" forms as well as file
upload forms, in mod_perl, without having to mess with CGI.pm (which I
saw a lot of people doing, and did not really understand very well) and
without having to do custom things when you have a file upload.

Comments welcome, YMMV, Caveat Emptor, and all that.

-- 
Rich Bowen
Apache Administrators Handbook
ApacheAdmin.com

Reply via email to