[svn:perlfaq] r11087 - perlfaq/trunk

[email protected] Tue, 15 Apr 2008 09:02:14 -0700 (PDT)
Newsgroups perl.cvs.perlfaq
Message-ID <[email protected]>
Author: comdog
Date: Tue Apr 15 09:02:13 2008
New Revision: 11087

Modified:
   perlfaq/trunk/perlfaq9.pod

Log:
* perlfaq9: How do I decode or create those %-encodings on the web?
	+ rewrote answer to use URI::Escape (suggested by Ben Bullock)
	+ escape() is no longer documented in CGI.pm, so removed



Modified: perlfaq/trunk/perlfaq9.pod
==============================================================================
--- perlfaq/trunk/perlfaq9.pod	(original)
+++ perlfaq/trunk/perlfaq9.pod	Tue Apr 15 09:02:13 2008
@@ -270,27 +270,46 @@
     $content = $ua->request($req)->as_string;
 
 =head2 How do I decode or create those %-encodings on the web?
+X<URI> X<CGI.pm> X<CGI> X<URI::Escape> X<RFC 2396>
 
-If you are writing a CGI script, you should be using the CGI.pm module
-that comes with perl, or some other equivalent module.  The CGI module
-automatically decodes queries for you, and provides an escape()
-function to handle encoding.
-
-The best source of detailed information on URI encoding is RFC 2396.
-Basically, the following substitutions do it:
-
-    s/([^\w()'*~!.-])/sprintf '%%%02x', ord $1/eg;   # encode
-
-    s/%([A-Fa-f\d]{2})/chr hex $1/eg;                # decode
-	s/%([[:xdigit:]]{2})/chr hex $1/eg;          # same thing
-
-However, you should only apply them to individual URI components, not
-the entire URI, otherwise you'll lose information and generally mess
-things up.  If that didn't explain it, don't worry.  Just go read
-section 2 of the RFC, it's probably the best explanation there is.
+(contributed by brian d foy)
 
-RFC 2396 also contains a lot of other useful information, including a
-regexp for breaking any arbitrary URI into components (Appendix B).
+Those C<%> encodings handle reserved characters in URIs, as described
+in RFC 2396, Section 2. This encoding replaces the reserved character
+with the hexadecimal representation of the character's number from
+the US-ASCII table. For instance, a colon, C<:>, becomes C<%3A>.
+
+In CGI scripts, you don't have to worry about decoding URIs if you are
+using C<CGI.pm>. You shouldn't have to process the URI yourself,
+either on the way in or the way out.
+
+If you have to encode a string yourself, remember that you should
+never try to encode an already-composed URI. You need to escape the
+components separately then put them together. To encode a string, you
+can use the the C<URI::Escape> module. The C<uri_escape> function
+returns the escaped string:
+
+	my $original = "Colon : Hash # Percent %";
+	
+	my $escaped = uri_escape( $original )
+	
+	print "$string\n"; # 'Colon%20%3A%20Hash%20%23%20Percent%20%25%20'
+
+To decode the string, use the C<uri_unescape> function:
+
+	my $unescaped = uri_unescape( $escaped );
+	
+	print $unescaped; # back to original
+	
+If you wanted to do it yourself, you simply need to replace the
+reserved characters with their encodings. A global substitution
+is one way to do it:
+
+	# encode
+	$string =~ s/([^^A-Za-z0-9\-_.!~*'()])/ sprintf "%%%0x", ord $1 /eg;
+	
+	#decode
+	$string =~ s/%([A-Fa-f\d]{2})/chr hex $1/eg;
 
 =head2 How do I redirect to another page?