
=head1 NAME

CGI::PathInfo - A lightweight CGI processing package for using CGI PATH_INFO as if it was GET method form parameters

=head1 SYNOPSIS

 use CGI::PathInfo;

 my $path_info = CGI::PathInfo->new;
 my ($form_field_value) = $path_info->param('some_field_name');

=head1 DESCRIPTION

Provides a micro-weight equivalent to the CPAN CGI.pm module
that permits the use of the CGI environment
variable 'PATH_INFO' as a functional equivalent to
the GET method 'QUERY_STRING'. This lets you use 'extra' URL
path information as CGI parameters.

For example, lets say you have a CGI script at URL
http://localhost/cgi-bin/myscript

If you were to call it as:

http://localhost/cgi-bin/myscript/some-thing/another-something/

your webserver should place '/some-thing/another-thing/' into the
PATH_INFO environment variable when your script is run. CGI::PathInfo
lets you treat that information as if it were ordinary CGI form data.

An Example:

You call http://localhost/cgi-bin/myscript/some-thing/another-something/
on your webserver. 'myscript' contains:

  #!/usr/bin/perl -Tw

  use strict;
  use CGI::PathInfo;

  my $path_info = CGI::PathInfo->new;
  my $some      = $path_info->param('some'};
  my $another   = $path_info->param('another');

At this point '$some' should contain the value 'thing' and
'$another' should contain the value 'something'.

This is B<independant> of the use of ordinary CGI parameters. It is perfectly OK
to use I<both> the PATH_INFO and normal CGI parameters at the same time.

Example:

You call http://localhost/cgi-bin/myscript/some-thing/another-something/?a=b
on your webserver. 'myscript' contains:

  #!/usr/bin/perl -Tw

  use strict;
  use CGI::PathInfo;
  use CGI::Minimal;

  my $path_info = CGI::PathInfo->new;
  my $some      = $path_info->param('some'};
  my $another   = $path_info->param('another');

  my $cgi       = CGI::Minimal->new;
  my $a_value   = $cgi->param('a');

At this point '$some' should contain the value 'thing',
'$another' should contain the value 'something'. and
'$a_value' should contain the value 'b'.

Rather than attempt to address every possible need of a CGI
programmer, it provides the _minimum_ functions needed for CGI such
as parameter decoding, URL encoding and decoding.

The parameters decoding interface is somewhat compatible with the
CGI.pm module. No provision is made for generating HTTP or HTML
on your behalf - you are expected to be conversant with how
to put together any HTML or HTTP you need.

CGI::PathInfo is compatible with ModPerl 1 in addition to normal CGI.

=head1 CHANGES

  1.04 2020.09.26     - Maintainer update. Relicensed under the MIT License.
                        Minor tweaks to build process. Added meta_merge
                        information for GitHub. Added 'use warnings'.
 
  1.03 2008.07.22     - Updated for ModPerl2 compatibility

  1.02 2005.10.08     - Extended test coverage to 100% of code, fixed bug
                       with the 'stripleadingslash', 'striptrailingslash'
                       code, added documentation of all instantation parameters
                       to 'new' method, fixed missing 'Build.PL' declaration
                       in MANIFEST. Fixed mis-calls of 'croak' after delayed
                       load in error paths.

  1.01 2005.09.30    - Seperated POD into .pod file. Added more build tests.
                       Added Build.PL, META.yml, GPL_License.txt, 
                       Artistic_License.txt, LICENSE. Deferred loading
                       of Carp and HTML::Entities unless needed.
                       
                       Removed dependency on 'vars'.  Fixed error in output
                       HTML from the 'calling_parms_table' method.

                       Extended documentation to explain what the module
                       is used for more clearly.
 
  1.00 22 July 2000 - Initial public release.

=head1 METHODS

=over 4

=item new;

Creates a new instance of the CGI::PathInfo object and decodes
any 'PATH_INFO' parameters.

Example:

 use CGI::PathInfo;

 my $path_info = CGI::PathInfo->new;

The defaults are for the parameters to be seperated by '/' characters
with name/value pairs linked by '-' and with leading or trailing
'/' characters ignored.

  Example:

   $ENV{'PATH_INFO'} = '/yesterday-monday/tomorrow-wednesday/';

   decodes to

    'yesterday' -> 'monday'

    'tomorrow'  -> 'wednesday'

Values are read using the 'param' method.

Any of the defaults may be overridden by specifying them in the
invokation of 'new'.

Example:

  my $path_info = CGI::PathInfo->new({  Eq                 => '=',
                                        SplitOn            => '&',
                                        StripLeadingSlash  => 0,
                                        StripTrailingSlash => 0,
                });

The C<Eq> parameter declares the key/value seperator, C<SplitOn>
declares the parameter tuples seperator, C<StripLeadingSlash> turns
on (or off) the stripping of '/' characters from the front of the
path, C<StripTrailingSlash> does the same for the end of the path string.

It is probably a Bad Idea (tm) to set the Eq or SplitOn
values to a letter or a number (A-Za-z0-9) unless you
are a wizard at encodings.

The defaults were chosen to maximize the likelyhood that CGI
backed URLs will be crawled by search engines and that
MSIE won't try something stupid because of a '.tla' on a URL.

=back

=over 4

=item param([$fieldname]);

Called as C<$path_info-E<gt>param();> it returns the list of all defined
parameter fields in the same order they appear in the data in
PATH_INFO.

Called as C<$path_info-E<gt>param($fieldname);> it returns the value (or
array of values for multiple occurances of the same field name) assigned
to that $fieldname. If there is more than one value, the values are
returned in the same order they appeared in the data from user agent.

If called in a scalar context when several values are present for
specified parameter, the *first* value will be returned.

Examples:

  my (@form_fields) = $path_info->param;

  my (@multi_pick_field) = $path_info->param('pick_field_name');

  my ($form_field_value) = $path_info->param('some_field_name');

You can also use the param method to set param values to new values.
These values will be returned by this CGI::PathInfo object
as if they had been found in the originally processed PATH_INFO data. This
will not affect a seperately created instance of CGI::PathInfo.

Examples:

    $path_info->param( 'name' => 'Joe Shmoe' );

    $path_info->param({ 'name' => 'Joe Shmoe', 'birth_date' => '06/25/1966' });

    $path_info->param({ 'pick_list' => ['01','05','07'] });

=back

=over 4

=item calling_parms_table;

Returns a formatted HTML table containing all the PATH_INFO parameters
for debugging purposes

Example:

  print $path_info->calling_parms_table;

=back

=over 4

=item url_encode($string);

Returns a URL encoding of the input string.
Anything except 0-9a-zA-Z is escaped to %xx form.

The idea is to reserve all other characters for potential use
as parameter or key/value seperators.

Example:

 my $url_encoded_string = $path_info->url_encode($string);

=back

=over 4

=item url_decode($string);

Returns URL *decoding* of input string (%xx substitutions
are decoded to their actual values).

Example:

 my $url_decoded_string = $path_info->url_decode($string);

=back

=head1 BUGS

None known.

=head1 TODO

Extend build tests. Investigate ModPerl2 compatibility.

=head1 AUTHORS

Jerilyn Franz <cpan@jerilyn.info>

=head1 VERSION

1.04 - released 2020.09.26

=head1 COPYRIGHT

Copyright (c) Jerilyn Franz and FreeRun Technologies. All rights reserved.

=head1 LICENSE

MIT License

Copyright (c) 2020 Jerilyn Franz

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

=head1 DISCLAIMER

THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS
OR IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
PARTICULAR PURPOSE.

Use of this software in any way or in any form, source or binary,
is not allowed in any country which prohibits disclaimers of any
implied warranties of merchantability or fitness for a particular
purpose or any disclaimers of a similar nature.

IN NO EVENT SHALL I BE LIABLE TO ANY PARTY FOR DIRECT, INDIRECT,
SPECIAL, INCIDENTAL,  OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE
USE OF THIS SOFTWARE AND ITS DOCUMENTATION (INCLUDING, BUT NOT
LIMITED TO, LOST PROFITS) EVEN IF I HAVE BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGE

=cut

