Browse files

Fix RT-83761. Lower-cased encoded characters were not being decoded

Thanks to David Arenillas for reporting it.
  • Loading branch information...
1 parent cc93c45 commit 9d2441f368be8753c7f95194245ae7fd3e516044 @mithun committed Mar 4, 2013
Showing with 74 additions and 39 deletions.
  1. +1 −2 Build.PL
  2. +25 −25 lib/URI/Encode.pm
  3. +48 −12 t/01-basic.t
View
3 Build.PL
@@ -33,8 +33,7 @@ my $builder = Module::Build->new(
meta_merge => {
keywords => [qw(uri escape encode percent)],
resources => {
- bugtracker =>
- 'http://rt.cpan.org/Public/Dist/Display.html?Name=URI-Encode',
+ bugtracker => 'http://rt.cpan.org/Public/Dist/Display.html?Name=URI-Encode',
repository => 'git://github.com/mithun/perl-uri-encode.git',
homepage => 'https://github.com/mithun/perl-uri-encode',
},
View
50 lib/URI/Encode.pm
@@ -29,7 +29,7 @@ our (@EXPORT_OK);
# Reserved characters
my $reserved_re
- = qr{([^a-zA-Z0-9\-\_\.\~\!\*\'\(\)\;\:\@\&\=\+\$\,\/\?\#\[\]\%])}x;
+ = qr{([^a-zA-Z0-9\-\_\.\~\!\*\'\(\)\;\:\@\&\=\+\$\,\/\?\#\[\]\%])}x;
# Un-reserved characters
my $unreserved_re = qr{([^a-zA-Z0-9\Q-_.~\E\%])}x;
@@ -69,17 +69,15 @@ sub new {
%{$input},
# Encoding Map
- enc_map =>
- { ( map { chr($_) => sprintf( "%%%02X", $_ ) } ( 0 ... 255 ) ) },
+ enc_map => { ( map { chr($_) => sprintf( "%%%02X", $_ ) } ( 0 ... 255 ) ) },
# Decoding Map
- dec_map =>
- { ( map { sprintf( "%02X", $_ ) => chr($_) } ( 0 ... 255 ) ) },
+ dec_map => { ( map { sprintf( "%02X", $_ ) => chr($_) } ( 0 ... 255 ) ), },
};
# Return
my $self = bless $options, $class;
- return $self;
+ return $self;
} ## end sub new
#######################
@@ -90,17 +88,16 @@ sub encode {
# Check for data
# Allow to be '0'
- return unless defined $data;
+ return unless defined $data;
my $enc_res = $self->{encode_reserved};
my $double_encode = $self->{double_encode};
if ( defined $options ) {
if ( ref $options eq 'HASH' ) {
- $enc_res = $options->{encode_reserved}
- if exists $options->{encode_reserved};
+ $enc_res = $options->{encode_reserved} if exists $options->{encode_reserved};
$double_encode = $options->{double_encode}
- if exists $options->{double_encode};
+ if exists $options->{double_encode};
} ## end if ( ref $options eq 'HASH')
else {
$enc_res = $options;
@@ -123,7 +120,7 @@ sub encode {
}
# Done
- return $data;
+ return $data;
} ## end sub encode
#######################
@@ -134,12 +131,12 @@ sub decode {
# Check for data
# Allow to be '0'
- return unless defined $data;
+ return unless defined $data;
# Percent Decode
$data =~ s{$encoded_chars}{ $self->_get_decoded_char($1) }gex;
- return $data;
+ return $data;
} ## end sub decode
#######################
@@ -156,28 +153,31 @@ sub uri_decode { return __PACKAGE__->new()->decode(@_); }
# INTERNAL
#######################
+
sub _get_encoded_char {
my ( $self, $char ) = @_;
- return $self->{enc_map}->{$char} if exists $self->{enc_map}->{$char};
- return $char;
-}
+ return $self->{enc_map}->{$char} if exists $self->{enc_map}->{$char};
+ return $char;
+} ## end sub _get_encoded_char
+
sub _encode_literal_percent {
my ( $self, $char, $post ) = @_;
- return $self->_get_encoded_char($char) if not defined $post;
+ return $self->_get_encoded_char($char) if not defined $post;
if ( $post =~ m{^([a-fA-F0-9]{2})}x ) {
- return $self->_get_encoded_char($char)
- unless exists $self->{dec_map}->{$1};
- return $char;
- }
- return $self->_get_encoded_char($char);
+ return $self->_get_encoded_char($char) unless exists $self->{dec_map}->{$1};
+ return $char;
+ } ## end if ( $post =~ m{^([a-fA-F0-9]{2})}x)
+ return $self->_get_encoded_char($char);
} ## end sub _encode_literal_percent
+
sub _get_decoded_char {
my ( $self, $char ) = @_;
- return $self->{dec_map}->{$char} if exists $self->{dec_map}->{$char};
- return $char;
-}
+ return $self->{dec_map}->{ uc($char) }
+ if exists $self->{dec_map}->{ uc($char) };
+ return $char;
+} ## end sub _get_decoded_char
#######################
1;
View
60 t/01-basic.t
@@ -12,26 +12,44 @@ BEGIN { use_ok( "URI::Encode", qw(uri_encode uri_decode) ); }
# Define URI's
my $url
- = "http://mithun.aÿachit.com/my pages.html?name=m!thun&Yours=w%hat?#";
+ = "http://mithun.aÿachit.com/my pages.html?name=m!thun&Yours=w%hat?#";
my $encoded
- = "http://mithun.a%C3%83%C2%BFachit.com/my%20pages.html?name=m!thun&Yours=w%25hat?#";
+ = "http://mithun.a%C3%83%C2%BFachit.com/my%20pages.html?name=m!thun&Yours=w%25hat?#";
my $encoded_reserved
- = "http%3A%2F%2Fmithun.a%C3%83%C2%BFachit.com%2Fmy%20pages.html%3Fname%3Dm%21thun%26Yours%3Dw%25hat%3F%23";
+ = "http%3A%2F%2Fmithun.a%C3%83%C2%BFachit.com%2Fmy%20pages.html%3Fname%3Dm%21thun%26Yours%3Dw%25hat%3F%23";
# Test Init
my $uri = new_ok("URI::Encode");
can_ok( $uri, qw(encode decode) );
# Test OOP
is( $uri->encode($url), $encoded, 'OOP: Unreserved encoding' );
-is( $uri->encode( $url, { encode_reserved => 1, } ),
- $encoded_reserved, 'OOP: Reserved Encoding with HASH options' );
+is(
+ $uri->encode(
+ $url, {
+ encode_reserved => 1,
+ }
+ ),
+ $encoded_reserved,
+ 'OOP: Reserved Encoding with HASH options'
+);
is( $uri->encode( $url, 1 ),
$encoded_reserved, 'OOP: Reserved Encoding with scalar option' );
-is( $uri->encode( $encoded_reserved, { double_encode => 0, } ),
- $encoded_reserved, 'OOP: Double encoding OFF' );
is(
- $uri->encode( 'This is a %20 test', { double_encode => 1, } ),
+ $uri->encode(
+ $encoded_reserved, {
+ double_encode => 0,
+ }
+ ),
+ $encoded_reserved,
+ 'OOP: Double encoding OFF'
+);
+is(
+ $uri->encode(
+ 'This is a %20 test', {
+ double_encode => 1,
+ }
+ ),
'This%20is%20a%20%2520%20test',
'OOP: Double encoding ON'
);
@@ -43,13 +61,31 @@ can_ok( "URI::Encode", qw(uri_encode uri_decode) );
is( uri_encode($url), $encoded, 'Function: Unreserved encoding' );
is( uri_encode( $url, 1 ),
$encoded_reserved, 'Function: Reserved encoding with scalar option' );
-is( uri_encode( $url, { encode_reserved => 1, } ),
- $encoded_reserved, 'Function: Reserved encoding with named option' );
-is( uri_encode( $encoded_reserved, { double_encode => 0, } ),
- $encoded_reserved, 'Function: Double encoding OFF' );
+is(
+ uri_encode(
+ $url, {
+ encode_reserved => 1,
+ }
+ ),
+ $encoded_reserved,
+ 'Function: Reserved encoding with named option'
+);
+is(
+ uri_encode(
+ $encoded_reserved, {
+ double_encode => 0,
+ }
+ ),
+ $encoded_reserved,
+ 'Function: Double encoding OFF'
+);
is( Encode::decode( 'utf-8-strict', uri_decode($encoded) ),
$url, 'Function: Decoding' );
+## Test Lowercase & Uppercase decode
+is( $uri->decode('foo%2bbar'), 'foo+bar', 'Lower cased decoding' );
+is( $uri->decode('foo%2Bbar'), 'foo+bar', 'Upper cased decoding' );
+
## Done
done_testing();
exit 0;

0 comments on commit 9d2441f

Please sign in to comment.