URI.escape_component

 JavaScript の escapeURIComponent() 相当の関数ってありましたっけ?
もしなければURIãƒ¢ã‚¸ãƒ¥ãƒ¼ãƒ«ã«è¿½åŠ ã™ã‚‹ã®ã¯ã©ã†ã§ã™ã‹ã€‚

 ドキュメントの修正も混ざっていますが、以下がパッチです。

Index: lib/uri/common.rb

— lib/uri/common.rb (revision 24684)
+++ lib/uri/common.rb (working copy)
@@ -70,6 +70,7 @@ module URI
#
# * :ESCAPED (URI::PATTERN::ESCAPED in default)
# * :UNRESERVED (URI::PATTERN::UNRESERVED in default)

  • * :RESERVED (URI::PATTERN::RESERVED in default)

    * :DOMLABEL (URI::PATTERN::DOMLABEL in default)

    * :TOPLABEL (URI::PATTERN::TOPLABEL in default)

    * :HOSTNAME (URI::PATTERN::HOSTNAME in default)

@@ -226,6 +227,10 @@ module URI
end.force_encoding(Encoding::US_ASCII)
end

  • def escape_component(str, unsafe = @regexp[:NON_UNRESERVED])
  •  escape(str, unsafe)
    
  • end
  • def unescape(str, escaped = @regexp[:ESCAPED])
    str.gsub(escaped) { [$&[1, 2].hex].pack(‘C’)
    }.force_encoding(str.encoding)
    end
    @@ -408,6 +413,7 @@ module URI
    # for URI::escape/unescape
    ret[:ESCAPED] = Regexp.new(pattern[:ESCAPED])
    ret[:UNSAFE] =
    Regexp.new("[^#{pattern[:UNRESERVED]}#{pattern[:RESERVED]}]")
  •  ret[:NON_UNRESERVED] = Regexp.new("[^#{pattern[:UNRESERVED]}]")
    
     # for Generic#initialize
     ret[:SCHEME]   = Regexp.new("^#{pattern[:SCHEME]}$")
    

@@ -476,10 +482,10 @@ module URI
# == Args
#
# +str+::

  • String to replaces in.

  • String to escape.

    +unsafe+::

    Regexp that matches all symbols that must be replaced with

codes.

  • By default uses REGEXP::UNSAFE.

  • By default uses URI::UNSAFE.

    When this argument is a String, it represents a character set.

    == Description

@@ -529,6 +535,36 @@ module URI
DEFAULT_PARSER.unescape(*arg)
end
alias decode unescape

  • == Synopsis

  • URI.escape_component(str)

  • == Args

  • +str+::

  • String to escape.

  • +unsafe+::

  • Regexp that matches all symbols that must be replaced with

codes.

  • By default uses URI::NON_UNRESERVED.

  • When this argument is a String, it represents a character set.

  • == Description

  • This function is a version of escape() to escape a string for use

  • in URI query components.

  • == Usage

  • require ‘uri’

  • uri = URI.parse(“http://example.com/plot?q=” +

URI.escape_component(“y=2x”))

extend Escape
Index: test/uri/test_common.rb

— test/uri/test_common.rb (revision 24684)
+++ test/uri/test_common.rb (working copy)
@@ -49,6 +49,40 @@ class TestCommon < Test::Unit::TestCase
assert_equal(expected, Kernel::URI(“http://www.ruby-lang.org/”))
assert_raise(NoMethodError) {
Object.new.URI(“http://www.ruby-lang.org/”) }
end
+

  • RESERVED = /\A[;/?:@&=+$,[]]\z/
  • UNRESERVED = /\A[-_.!~*’()A-Za-z0-9]\z/
  • def test_escape
  • unescaped = ‘’
  • escaped = ‘’
  • escaped_component = ‘’
  • (0x00…0x7f).map { |c|
  •  ch = c.chr
    
  •  esc = '%%%02X' % c
    
  •  unescaped << ch
    
  •  case ch
    
  •  when UNRESERVED
    
  •    escaped << ch
    
  •    escaped_component << ch
    
  •  when RESERVED
    
  •    escaped << ch
    
  •    escaped_component << esc
    
  •  else
    
  •    escaped << esc
    
  •    escaped_component << esc
    
  •  end
    
  • }
  • assert_equal(escaped, URI.escape(unescaped))
  • assert_equal(escaped_component, URI.escape_component(unescaped))
  • assert_equal(unescaped, URI.unescape(escaped))
  • assert_equal(unescaped, URI.unescape(escaped_component))
  • end
    end

[email protected]@%$G$9!#e(B

Akinori MUSHA wrote:

e$B!!e(BJavaScript e$B$Ne(B escapeURIComponent() e$BAjEv$N4X?t$C$F$"$j$^$7$?$C$1!)e(B
e$B$b$7$J$1$l$Pe(BURIe$B%b%8%e!<%k$KDI2C$9$k$N$O$I$&$G$9$+!#e(B

encodeURIComponent e$B$G$O$"$j$^$;$s$+!)e(B

e$B$5$F$*$-!"e(BURI.escapee$B$OFHFC$NF0$-$r$9$k$N$G!"e(BJavaScript/ECMAScript
e$B$Ne(B
escape e$B$H$be(B encodeURI e$B$H$be(B encodeURIComponent
e$B$H$b0c$$$^$9!#e(B

e$B$=$&$$$($P!"8=:_$N;EMM$N0U?^$r$*[email protected]$C$?e(B
[ruby-dev:38124]

e$B$J$*!“LLE]$JOC$,=P$F$-$?;~$K$O!”$H$j$"$($:e(B akr e$B$5$s$,e(B
e$B4{$K<h$j>e$2$F$$$J$$$+D4$Y$k$o$1$G$9$,!"$d$C$Q$j07$C$F$$$k$o$1$G$9!#e(B
http://www.a-k-r.org/d/d2004_07.html
https://www.codeblog.org/blog/akr/20070222.html

(2009e$BG/e(B08e$B7ne(B28e$BF|e(B 21:09), Akinori MUSHA
e$B$5$s$O=q$-$^$7$?e(B:

e$B!!e(BJavaScript e$B$Ne(B escapeURIComponent() e$BAjEv$N4X?t$C$F$"$j$^$7$?$C$1!)e(B
e$B$b$7$J$1$l$Pe(BURIe$B%b%8%e!<%k$KDI2C$9$k$N$O$I$&$G$9$+!#e(B

e$B;d$H$7$F$OFCJL$K0U8+$O$J$$$G$9!#e(B
e$BB>$K0U8+$,$J$1$l$PDI2C$7$F$7$^$C$F9=$o$J$$$H;W$$$^$9!#e(B

escapee$B7O$OJL$K$^$H$^$C$F$k$H;H$$0W$$$_$?$$$JOC$,e(B

e$B$I$3$+$G=P$F$$$?$N$G$O$J$+$C$?$+$J$H;W$$$^$9!#e(B

e$B$=$&$J$C$F$k$H$$$$$J!<$H$O;W$$$^$9!#e(B

At Fri, 28 Aug 2009 22:34:46 +0900,
NARUSE, Yui wrote:

Akinori MUSHA wrote:

 JavaScript の escapeURIComponent() 相当の関数ってありましたっけ?
もしなければURIãƒ¢ã‚¸ãƒ¥ãƒ¼ãƒ«ã«è¿½åŠ ã™ã‚‹ã®ã¯ã©ã†ã§ã™ã‹ã€‚

encodeURIComponent ではありませんか?

 そうでした。

さておき、URI.escapeは独特の動きをするので、JavaScript/ECMAScript の
escape とも encodeURI とも encodeURIComponent とも違います。

そういえば、現在の仕様の意図をお聞きしたかったんだった
[ruby-dev:38124]

 私も知りたいと思います。そして、HTTP URIパラメータを現実世界で
扱う際に典型的に必要な機能はURIモジュールが備えていてほしい。

 CGIやWEBrickにあってもレイヤが違うので外から呼び出そうとは思わ
ないし、そこはきっちり拾い上げたいところです。

なお、面倒な話が出てきた時には、とりあえず akr さんが
既に取り上げていないか調べるわけですが、やっぱり扱っているわけです。
http://www.a-k-r.org/d/d2004_07.html
https://www.codeblog.org/blog/akr/20070222.html

 未だに encodeURIComponent() すらないのでその先に進めないんです
よね。手元では Perl の URI::QueryParam 相当を作っているんですが、
URI との関係をどうしようか悩んでいるところです。とりあえず URI の
方針を明らかにしていくところからでしょうか。

[email protected]@%$G$9!#e(B

2009/09/02 16:28, akira yamada / e$B$d$^[email protected]$"$-$ie(B wrote:

(2009e$BG/e(B08e$B7ne(B28e$BF|e(B 21:09), Akinori MUSHA e$B$5$s$O=q$-$^$7$?e(B:

e$B!!e(BJavaScript e$B$Ne(B escapeURIComponent() e$BAjEv$N4X?t$C$F$"$j$^$7$?$C$1!)e(B
e$B$b$7$J$1$l$Pe(BURIe$B%b%8%e!<%k$KDI2C$9$k$N$O$I$&$G$9$+!#e(B

e$B;d$H$7$F$OFCJL$K0U8+$O$J$$$G$9!#e(B
e$BB>$K0U8+$,$J$1$l$PDI2C$7$F$7$^$C$F9=$o$J$$$H;W$$$^$9!#e(B

e$BA02s$O%Q%C%A$^$G8+$F$J$+$C$?$s$G$9$,!"e(B
URI.escape_component e$B$N0z?t$Oe(B str
e$B$N$_$NJ}$,$$$$$N$G$O$J$$$G$7$g$&$+!#e(B
e$BCV49%Q%?!<%s$rM?$($i$l$kI,MW$OL5$$$h$&$K;W$($^$9!#e(B
e$B<BAu$be(B String#gsub(pattern, hash) e$B$r;H$C$?J}$,B.$$$G$9$+$M!#e(B

escapee$B7O$OJL$K$^$H$^$C$F$k$H;H$$0W$$$_$?$$$JOC$,e(B

e$B$I$3$+$G=P$F$$$?$N$G$O$J$+$C$?$+$J$H;W$$$^$9!#e(B

e$B$=$&$J$C$F$k$H$$$$$J!<$H$O;W$$$^$9!#e(B

[email protected]$5$l$?$s$G$9$,!"7k6Ie(B String#gsub(pattern, hash)
e$B$H$$$&[email protected]$G$7$?$M!#e(B
e$B$^$!!"e(BURI e$B7O$Oe(B URI e$B$G$$$$5$$,$7$^$9!#e(B