14

page_urlそのため、Rails URLヘルパー( )を使用して、アンパサンドなどの特殊文字を含むURLを作成しようとしています。ほとんどの場合、期待どおりに機能します。

(rdb:1) page_url('foo', :host => 'host')
"http://host/pages/foo"
(rdb:1) page_url('foo_%_bar', :host => 'host')
"http://host/pages/foo_%25_bar"

しかし、いくつかの奇妙な理由で、アンパサンドはエスケープされません。

(rdb:1) page_url('foo_&_bar', :host => 'host')
"http://host/pages/foo_&_bar"

そして、私がそれらを事前にエスケープすると、それらは破損します:

(rdb:1) page_url('foo_%26_bar', :host => 'host')
"http://host/pages/foo_%2526_bar"

CGI::escape、一方、それらをうまく逃がします:

(rdb:1) CGI::escape('foo_&_bar')
"foo_%26_bar"

何が起こっているのですか、そしてこれをどのように回避しますか?(より良いものでgsub('&', '%26')、それはです。)

4

2 に答える 2

17

私はあなたにそれを扱うより良い方法を言うことはできません-しかし私はそれが起こっている理由を説明することができます。

アンパサンドは、URLの無効な文字ではありません。そうしないと、「http:// host / pages / foo?bar = baz&style=foo_style」などの問題が発生します。

編集:ソースコードを深く掘り下げると、Railsはパラメータに対してのみCGI.escapeを使用しているように見えます。

ヘルパーのurl-generatorsはurl_for(内部)を使用します。これは最終的に次のように呼び出します。http://apidock.com/rails/ActionController/Routing/Route/generate ソースコードのsprivate-methodsの奥深くにあるものを呼び出します。 。しかし、最終的にはCGI.escapeを呼び出すことになります(最初にactionpack / lib / action_controller / routing / route.rbを調べ、次にactionpack / lib / action_controller / routing / segments.rbを調べます)。

最終結果は、UR​​L自体で、railsがURI.escapeを使用することです。これは特にアンパサンドをまったく更新しません。

>> CGI.escape('/my_foo_&_bar')
=> "%2Fmy_foo_%26_bar"
>> URI.escape('/my_foo_&_bar')
=> "/my_foo_&_bar"

現在、実際の機能要求をRailsチームに提出せずに、これについてできることは何もありません。

... URLにアンパサンドを使用しないことを選択するオプションがない限り、すべてのURLに対していつでもアンパサンドを自分でgsubすることができます。

def my_clean_url(the_url)
   return the_url.gsub(/&/,'_')
end
>> my_clean_url('/my_foo_&_bar')
=> "/my_foo___bar"

page_url(my_clean_url('/my_foo_&_bar'))
于 2011-03-22T16:34:49.087 に答える
11

az、AZ、0-9およびアンダースコア以外のものをエンコードしようとしているすべての人のために:

URI.encode(string, /\W/)

たとえば、アンパサンドを含む可能性のあるコンテンツがあり、このコンテンツをリンクbodyのパラメーターとして使用したいとします。がないと、アンパサンド(安全なURI文字)はエンコードされないため、リンクが部分的に切断されます。mailto/\W/

于 2016-09-22T17:10:36.517 に答える