Project

General

Profile

Actions

Feature #542

closed

cgi.rb : CGI::unescape return encoding

Added by xibbar (Takeyuki FUJIOKA) over 15 years ago. Updated almost 13 years ago.

Status:
Rejected
Target version:
-
[ruby-dev:36132]

Description

=begin
CGI::unescapeは現在は引数のencodingでforce_encodingするように
なっていますが、ascii_only?がtrueの場合はUS-ASCII、
falseの場合はASCII-8BITを返すのがいいと思います。

Index: lib/cgi.rb

--- lib/cgi.rb (リビジョン 19071)
+++ lib/cgi.rb (作業コピー)
@@ -349,10 +349,10 @@
# string = CGI::unescape("%27Stop%21%27+said+Fred")
# # => "'Stop!' said Fred"
def CGI::unescape(string)

  • enc = string.encoding
  • string.tr('+', ' ').gsub(/((?:%[0-9a-fA-F]{2})+)/) do
  •  [$1.delete('%')].pack('H*').force_encoding(enc)
    
  • str=string.tr('+', ' ').gsub(/((?:%[0-9a-fA-F]{2})+)/) do
  •  [$1.delete('%')].pack('H*')
    
    end
  • str.ascii_only? ? str.force_encoding("US-ASCII") : str.force_encoding("ASCII-8BIT")
    end
TABLE_FOR_ESCAPE_HTML__ = {

=end

Actions #1

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
この修正のテストを追加
Index: test/cgi/test_cgi_class_method.rb

--- test/cgi/test_cgi_class_method.rb (リビジョン 0)
+++ test/cgi/test_cgi_class_method.rb (リビジョン 0)
@@ -0,0 +1,21 @@
+require 'test/unit'
+require 'cgi'
+
+
+class CGIClassMethodTest < Test::Unit::TestCase

  • def test_cgi_class_method_escape
  • assert_equal(CGI::unescape("Hello"),"Hello")
  • assert_equal(CGI::unescape("Hello%21%22%25%26%27%28%29-%3D%5E%7E%7C"),
  •  "Hello!\"#$\%&'()-=^~|")
    
  • unescaped=CGI::unescape("%E3%81%93%E3%82%93%E3%81%AB%E3%81%A1%E3%81%AF")
  • assert_equal(unescaped,"\xE3\x81\x93\xE3\x82\x93\xE3\x81\xAB\xE3\x81\xA1\xE3\x81\xAF")
  • if RUBY_VERSION>="1.9.0"
  •  assert_equal(CGI::unescape("Hello").encoding,Encoding::US_ASCII)
    
  •  assert_equal(CGI::unescape("Hello%21%22%25%26%27%28%29-%3D%5E%7E%7C").encoding,
    
  •               Encoding::US_ASCII)
    
  •  assert_equal(unescaped.encoding,Encoding::ASCII_8BIT)
    
  • end
  • end
    +end

=end

Actions #2

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

CGI::unescapeは現在は引数のencodingでforce_encodingするように
なっていますが、ascii_only?がtrueの場合はUS-ASCII、
falseの場合はASCII-8BITを返すのがいいと思います。

引数にもともと非ASCII文字が入っていた場合にはどうなりますかね。

その部分は何も変換されません。
エンコーディングはASCII-8BITになります。

=end

Actions #3

Updated by naruse (Yui NARUSE) over 15 years ago

=begin
成瀬です。

Takeyuki Fujioka wrote:

CGI::unescapeは現在は引数のencodingでforce_encodingするように
なっていますが、ascii_only?がtrueの場合はUS-ASCII、
falseの場合はASCII-8BITを返すのがいいと思います。

ascii_only? なときに US-ASCII を返すのはいいと思うのですが、
false なときに ASCII-8BIT はまずいですね。

HTTP ヘッダで charset を指定されつつ escape されて渡された場合、
とりあえず escape された文字列にその charset をつけ、
その後に unescape するってのはそれなりにありうる流れなので。

Ruby M17N では、一連の処理の結果の encoding を指定する際に、
引数の String#encodig を用いるということはしばしば行われます。

--
NARUSE, Yui

=end

Actions #4

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

Fujioka wrote:

CGI::unescapeは現在は引数のencodingでforce_encodingするように
なっていますが、ascii_only?がtrueの場合はUS-ASCII、
falseの場合はASCII-8BITを返すのがいいと思います。

ascii_only? なときに US-ASCII を返すのはいいと思うのですが、
false なときに ASCII-8BIT はまずいですね。

HTTP ヘッダで charset を指定されつつ escape されて渡された場合、
とりあえず escape された文字列にその charset をつけ、
その後に unescape するってのはそれなりにありうる流れなので。

クエリを渡された場合はそのクエリにencodingをつけて
unescapeするのではなくて、unescapeをしてから
encodingをつけるのが順番としては正しいと思います。
クエリは通常はascii文字列のはずなので、
それにencodingをつける方が間違っていると思います。

ただ、今思っているのはASCII以外はASCII-8BITになるのは
あんまりだと思っていて、CGI.newしたときにオプションで
期待するencodingを渡してあげれば
自動的にUS-ASCIIかそれ以外の場合はそのencodingにforce_encodingして
あげる機能が欲しいと思っています。
まだ抗争中ですが。

Ruby M17N では、一連の処理の結果の encoding を指定する際に、
引数の String#encodig を用いるということはしばしば行われます。

unescapeはasciiからasciiかどうかわからない文字列へのフィルタなので
引数のencodingはあてにできないと思っています。

=end

Actions #5

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

その部分は何も変換されません。
エンコーディングはASCII-8BITになります。

[ruby-dev:36138] の実装は (引数が ASCII-8BIT 以外で非ASCII文
字が入っていれば) 例外になりそうですが、そんなことはありませ
んか?

つまりencodingが間違っている場合ということですか?
その場合は例外でもいいような。。。
ASCII-8BITに変換してから処理して例外を出さない方がいいでしょうか?

=end

Actions #6

Updated by ko1 (Koichi Sasada) over 15 years ago

  • Assignee set to xibbar (Takeyuki FUJIOKA)

=begin

=end

Actions #7

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

  • Status changed from Open to Rejected

=begin
いずれencodingの自動付与機能を搭載するということで、
このチケットは閉じます。
=end

Actions #8

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

成瀬さんとやり取りをした結果、やはりヘッダのcharsetを見て
そのencodingをつけてあげるのが筋だろうという話になりました。

ブラウザはここで利用できる charset をつけてくれるんでしょう
か?

いえ、つけてくれません。
あくまでCGIアプリ側が期待することになります。

でも、例えばUTF-8を期待しているアプリにEUC-JPをポストして
例外が起きるのは好ましくありませんね。考えます。

=end

Actions #9

Updated by Tietew (Toru Iwase) over 15 years ago

=begin

On Wed, 10 Sep 2008 13:51:26 +0900
In article
[[ruby-dev:36239] Re: [Feature #542] cgi.rb : CGI::unescape return encoding]
Tanaka Akira wrote:

In article ,
Fujioka writes:

成瀬さんとやり取りをした結果、やはりヘッダのcharsetを見て
そのencodingをつけてあげるのが筋だろうという話になりました。

ブラウザはここで利用できる charset をつけてくれるんでしょう
か?

application/x-www-form-urlencoded にはそもそも charset がありませんし、
multipart/form-data にも charset が付いているのは見たことがないです。

--
Tietew
Blog: http://www.tietew.jp/
PGP: 26CB 71BB B595 09C4 0153 81C4 773C 963A D51B 8CAA

=end

Actions #10

Updated by Tietew (Toru Iwase) over 15 years ago

=begin

On Wed, 10 Sep 2008 14:33:34 +0900
In article
[[ruby-dev:36241] Re: [Feature #542] cgi.rb : CGI::unescape return encoding]
Fujioka wrote:

でも、例えばUTF-8を期待しているアプリにEUC-JPをポストして
例外が起きるのは好ましくありませんね。考えます。

期待しているのと違う文字セット、あるいは壊れた文字列を渡し、XSSを起こす
という攻撃があるので、むしろ例外の方がありがたいかもしれません。

begin
cgi = CGI.new(:assume_encoding => 'UTF-8')
rescue CGI::InvalidEncodingError
print "Status: 400 Bad Request\n\n"
exit
end

--
Tietew
Blog: http://www.tietew.jp/
PGP: 26CB 71BB B595 09C4 0153 81C4 773C 963A D51B 8CAA

=end

Actions #11

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

成瀬さんとやり取りをした結果、やはりヘッダのcharsetを見て
そのencodingをつけてあげるのが筋だろうという話になりました。
ブラウザはここで利用できる charset をつけてくれるんでしょう
か?

application/x-www-form-urlencoded にはそもそも charset がありませんし、
multipart/form-data にも charset が付いているのは見たことがないです。

encoding情報はもらえないので、期待するしかないです。
だからといってASCII-8BITかUS-ASCIIのどちらでしか
データを貰えないというのも面倒かなと思うのですが、
どうしたらいいと思いますか?

ポストされたデータは

1.ASCII-8BIT でもらう(現状)
2.US-ASCII or ASCII-8BIT でもらう
3.期待するencodingを決めて、US-ASCII or 期待するencodingでもらう
4.上記3に加えて、encodingチェックをおこなって、encodingが間違っている
場合はnilなどを返す

1と2は日本語のCGIアプリの出力が面倒です。
@cgi=CGI.new
したとして、ポストされたデータに日本語が入ってくると
"タイトル:#{@cgi['title']}"
これが例外です。
日本語文字列とASCII-8BITが連結できないためです。
これでは使いづらいなぁと思ってアイディアを模索している最中です。

=end

Actions #12

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

Tanaka Akira さんは書きました:

encoding情報はもらえないので、期待するしかないです。
だからといってASCII-8BITかUS-ASCIIのどちらでしか
データを貰えないというのも面倒かなと思うのですが、
どうしたらいいと思いますか?

アプリケーションが期待するエンコーディングを cgi.rb に
教えてやるしかないし、そうするのが良いと思います。

了解です。

仕様としてはブラウザがデータを送ってくる原因となった HTML の
form の accept-charset を cgi.rb に
教えてやる (ということにしておく) んじゃないでしょうか。

送られてくるFormにaccept-charsetをつけても、
IEもFirefoxも対応していないので、実質無意味だと思います。
hidden属性でaccept-charsetを送るということですか?
それだったら現実的かな。

まぁ、accept-charset に限らず form の情報を教えてやるといろ
いろ検査できていいかもしれませんが。

=end

Actions #13

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

Web サーバが form を含む HTML を送った時に、ブラウザがどのよ
うな charset で返事を Web サーバ返すべきかを accept-charset
のような明示的な形や、HTML 自体の encoding として暗黙な形で
指示しているので、その指示を cgi.rb に教えてやるという意味を
意図していました。

なお、手元の iceweasel 2.0.0.16 は accept-charset を理解して
従うようです。

やはり、明示的にcgi.rbのインスタンスに伝えておいた方がよさそうですね。
エラー処理とか何もまだないですが、
とりあえず下のパッチで以下のようなCGIアプリは動きます。
この方針としてはいかがでしょうか?>ほかの意見ありそうな方々

あと、エンコーディングが違う文字列を送りつけられた場合に
どうするかですが、

  1. 放置(おそらくどこかで例外を起こして止まる)
  2. 検証しておかしかったときはkeyごと無視する
  3. 検証しておかしかったときはkeyはあるけど中身をnilにする
  4. 検証しておかしかったときはvalueをASCII-8BITにしてしまう
    4が親切かなと思うのですが、ご意見よろしくお願いします。

#!/Users/fujioka/local/bin/ruby19

vim:fileencoding=UTF-8

require 'cgi'
@cgi=CGI.new("html3","UTF-8")
@header = { "type" => "text/html", "charset" => "UTF-8" }

@cgi.out(@header) do
@cgi.html do
@cgi.head{@cgi.title{"たいとる"}}+
@cgi.body do
"結果:#{@cgi['title']}"+
@cgi.form("action"=>@cgi.script_name) do
@cgi.text_field("name"=>"title")+
@cgi.hidden("name"=>"key","value"=>"value")+
@cgi.submit("value"=>"OK")
end
end
end
end

Index: lib/cgi/core.rb

--- lib/cgi/core.rb (revision 19280)
+++ lib/cgi/core.rb (working copy)
@@ -600,7 +600,7 @@

stdinput.read(Integer(env_table['CONTENT_LENGTH'])) or ''
else
read_from_cmdline

  •                end
    
  •                end.force_encoding(@encoding)
                 )
     end
    

@@ -667,7 +667,8 @@
# from the command line or (failing that) from standard input.
Otherwise,
# cookies and other parameters are parsed automatically from the standard
# CGI locations, which varies according to the REQUEST_METHOD.

  • def initialize(type = "query")
  • def initialize(type = "query",encoding="ASCII-8BIT")
  • @encoding=encoding
    if defined?(MOD_RUBY) && !ENV.key?("GATEWAY_INTERFACE")
    Apache.request.setup_cgi_env
    end

=end

Actions #14

Updated by znz (Kazuhiro NISHIYAMA) over 15 years ago

=begin
西山和広です。

At Sun, 14 Sep 2008 00:27:27 +0900,
Fujioka wrote:

あと、エンコーディングが違う文字列を送りつけられた場合に
どうするかですが、

  1. 放置(おそらくどこかで例外を起こして止まる)
  2. 検証しておかしかったときはkeyごと無視する
  3. 検証しておかしかったときはkeyはあるけど中身をnilにする
  4. 検証しておかしかったときはvalueをASCII-8BITにしてしまう
    4が親切かなと思うのですが、ご意見よろしくお願いします。

バイナリファイルのアップロードをするときに2や3だと困りそうです。

--
|ZnZ(ゼット エヌ ゼット)
|西山和広(Kazuhiro NISHIYAMA)

=end

Actions #15

Updated by Tietew (Toru Iwase) over 15 years ago

=begin

On Tue, 16 Sep 2008 17:33:08 +0900
In article 85r67k4h6t.wl%zn@mbf.nifty.com
[[ruby-dev:36321] Re: [Feature #542] cgi.rb : CGI::unescape return encoding]
Kazuhiro NISHIYAMA wrote:

あと、エンコーディングが違う文字列を送りつけられた場合に
どうするかですが、

  1. 放置(おそらくどこかで例外を起こして止まる)
  2. 検証しておかしかったときはkeyごと無視する
  3. 検証しておかしかったときはkeyはあるけど中身をnilにする
  4. 検証しておかしかったときはvalueをASCII-8BITにしてしまう
    4が親切かなと思うのですが、ご意見よろしくお願いします。

バイナリファイルのアップロードをするときに2や3だと困りそうです。

multipart/form-data で、かつ Content-Disposition filename を持っていれば
ASCII-8BIT で、そうでなければ検証 とか。

--
Tietew
Blog: http://www.tietew.jp/
PGP: 26CB 71BB B595 09C4 0153 81C4 773C 963A D51B 8CAA

=end

Actions #16

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

あと、エンコーディングが違う文字列を送りつけられた場合に
どうするかですが、

  1. 放置(おそらくどこかで例外を起こして止まる)
  2. 検証しておかしかったときはkeyごと無視する
  3. 検証しておかしかったときはkeyはあるけど中身をnilにする
  4. 検証しておかしかったときはvalueをASCII-8BITにしてしまう
    4が親切かなと思うのですが、ご意見よろしくお願いします。

バイナリファイルのアップロードをするときに2や3だと困りそうです。

ファイルは受取encodingが指定されていてもASCII-8BITが
適切じゃないかと思います。
ファイル以外の話だったら2とか3はいかがでしょう?

=end

Actions #17

Updated by naruse (Yui NARUSE) over 15 years ago

=begin
成瀬です。

Fujioka wrote:

あと、エンコーディングが違う文字列を送りつけられた場合に
どうするかですが、

  1. 放置(おそらくどこかで例外を起こして止まる)
  2. 検証しておかしかったときはkeyごと無視する
  3. 検証しておかしかったときはkeyはあるけど中身をnilにする
  4. 検証しておかしかったときはvalueをASCII-8BITにしてしまう
    4が親切かなと思うのですが、ご意見よろしくお願いします。
  1. かまわず指定された encoding をつける

じゃないですかね。
String#valid_encoding? で調べるとか、後で対処する方法はあるのですから。

--
NARUSE, Yui

=end

Actions #18

Updated by naruse (Yui NARUSE) over 15 years ago

=begin
成瀬です。

Fujioka wrote:

あと、エンコーディングが違う文字列を送りつけられた場合に
どうするかですが、

  1. 放置(おそらくどこかで例外を起こして止まる)
  2. 検証しておかしかったときはkeyごと無視する
  3. 検証しておかしかったときはkeyはあるけど中身をnilにする
  4. 検証しておかしかったときはvalueをASCII-8BITにしてしまう
    4が親切かなと思うのですが、ご意見よろしくお願いします。
    バイナリファイルのアップロードをするときに2や3だと困りそうです。

ファイルは受取encodingが指定されていてもASCII-8BITが
適切じゃないかと思います。
ファイル以外の話だったら2とか3はいかがでしょう?

バイナリファイルだったら ASCII-8BIT がよいですし、
テキストファイルならエンコーディング固定かもしれないわけで、
これも別途受け取り encoding を指定させるべきでしょう。

--
NARUSE, Yui

=end

Actions #19

Updated by Tietew (Toru Iwase) over 15 years ago

=begin

On Tue, 16 Sep 2008 21:37:12 +0900
In article
[[ruby-dev:36332] Re: [Feature #542] cgi.rb : CGI::unescape return encoding]
"NARUSE, Yui" wrote:

  1. かまわず指定された encoding をつける

じゃないですかね。
String#valid_encoding? で調べるとか、後で対処する方法はあるのですから。

bad knowhow になりそうで怖いです。

cgi = CGI.new('UTF-8')
unless cgi.param.join.valid_encoding?
print cgi.header('status' => '400 Bad Request')
print 'Bad Request'
exit
end

等のコードを毎度書くか俺ライブラリにする必要があるわけで。

--
Tietew
Blog: http://www.tietew.jp/
PGP: 26CB 71BB B595 09C4 0153 81C4 773C 963A D51B 8CAA

=end

Actions #20

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

  1. かまわず指定された encoding をつける

じゃないですかね。
String#valid_encoding? で調べるとか、後で対処する方法はあるのですから。

bad knowhow になりそうで怖いです。

bad knowhowになるぐらいだったら実装したいですね。

cgi = CGI.new('UTF-8')
unless cgi.param.join.valid_encoding?
print cgi.header('status' => '400 Bad Request')
print 'Bad Request'
exit
end

等のコードを毎度書くか俺ライブラリにする必要があるわけで。

これだとEUC-JPとUTF-8を送りつけられたときにjoinの時点で例外なような。
という話はさておき、
newするときのオプションで期待する挙動を切り替えられると
使いやすいでしょうかね?

cgi=CGI.new(:encoding=>"UTF-8",:element_encoding_check=>true)

みたいに。

=end

Actions #21

Updated by Tietew (Toru Iwase) over 15 years ago

=begin

On Wed, 17 Sep 2008 11:49:12 +0900
In article
[[ruby-dev:36342] Re: [Feature #542] cgi.rb : CGI::unescape return encoding]
Fujioka wrote:

藤岡です。

  1. かまわず指定された encoding をつける

じゃないですかね。
String#valid_encoding? で調べるとか、後で対処する方法はあるのですから。

bad knowhow になりそうで怖いです。

bad knowhowになるぐらいだったら実装したいですね。

cgi = CGI.new('UTF-8')
unless cgi.param.join.valid_encoding?
print cgi.header('status' => '400 Bad Request')
print 'Bad Request'
exit
end

等のコードを毎度書くか俺ライブラリにする必要があるわけで。

これだとEUC-JPとUTF-8を送りつけられたときにjoinの時点で例外なような。

force_encoding されている、という前提なので、例外はないはず。

newするときのオプションで期待する挙動を切り替えられると
使いやすいでしょうかね?

cgi=CGI.new(:encoding=>"UTF-8",:element_encoding_check=>true)

デフォルトチェックを希望。
混在したor不正なエンコーディングを受け付けることの方が例外的だと思います。
アップロードされたバイナリはもともと除外な訳で。

--
Tietew
Blog: http://www.tietew.jp/
PGP: 26CB 71BB B595 09C4 0153 81C4 773C 963A D51B 8CAA

=end

Actions #22

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

  1. かまわず指定された encoding をつける

じゃないですかね。
String#valid_encoding? で調べるとか、後で対処する方法はあるのですから。
bad knowhow になりそうで怖いです。

bad knowhowになるぐらいだったら実装したいですね。

cgi = CGI.new('UTF-8')
unless cgi.param.join.valid_encoding?
print cgi.header('status' => '400 Bad Request')
print 'Bad Request'
exit
end

等のコードを毎度書くか俺ライブラリにする必要があるわけで。

これだとEUC-JPとUTF-8を送りつけられたときにjoinの時点で例外なような。

force_encoding されている、という前提なので、例外はないはず。

newするときのオプションで期待する挙動を切り替えられると
使いやすいでしょうかね?

cgi=CGI.new(:encoding=>"UTF-8",:element_encoding_check=>true)

デフォルトチェックを希望。
混在したor不正なエンコーディングを受け付けることの方が例外的だと思います。
アップロードされたバイナリはもともと除外な訳で。

私としてはチェックを入れた方がいいと思っています。
cgi=CGI.new(:encoding=>"UTF-8",:element_encoding_check=>false)
こんな感じでできると楽かなと。
ファイルに関してはすべてASCII-8BITがいいと思っています。

=end

Actions #23

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

私としてはチェックを入れた方がいいと思っています。
cgi=CGI.new(:encoding=>"UTF-8",:element_encoding_check=>false)
こんな感じでできると楽かなと。
ファイルに関してはすべてASCII-8BITがいいと思っています。

  • CGI.newのオプションでHashも取れるようにする
    (現状は"html3"などのStringのみ)
  • CGIに@@encodingというクラス変数を用意し、default値は"UTF-8"とする
  • CGI::encodingとCGI::encoding=というメソッドを用意し、
    @@encodingのセッターとゲッターにする
  • CGI.newされたときにオプションで
    CGI.new(:encoding=>"EUC-JP")などと指定されない場合は
    @@encodingの値を@encodingに代入する
  • 各々のエレメントの値は@encodingの値でforce_encodingし、
    valid_encoding?する。ただし、fileだけはASCII-8BITとする。
  • オプションのときに:element_encoding_check=>falseが与えられたときは
    エンコーディングチェックしない。
  • encodingのチェックをして正しくない場合はASCII-8BITに
    force_encodingしてしまう

以上のような仕様ではいかがでしょうか?
サンプルベースで行くと、

require 'cgi'
@cgi=CGI.new("html3")

とやった場合は受け取った値はUTF-8とみなし、encodingのチェックを入れる。
タグメーカーはhtml3とする。
EUC-JPにする場合は

require 'cgi'
CGI::encoding="EUC-JP"
@cgi=CGI.new("html3")

もしくは

require 'cgi'
@cgi=CGI.new(:tag_maker=>"html3",:encoding=>"EUC-JP")

とする。エンコーディングのチェックをしない場合は

require 'cgi'
@cgi=CGI.new(:tag_maker=>"html3",:encoding=>"EUC-JP",:element_encoding_check=>false)

といったようにインスタンスへオプションで渡す。
以上のような使い勝手になります。

=end

Actions #24

Updated by znz (Kazuhiro NISHIYAMA) over 15 years ago

=begin
西山和広です。

At Sun, 21 Sep 2008 15:17:28 +0900,
Fujioka wrote:

  • 各々のエレメントの値は@encodingの値でforce_encodingし、
    valid_encoding?する。ただし、fileだけはASCII-8BITとする。

ファイルかどうかはどうやって判断するのでしょうか?

--
|ZnZ(ゼット エヌ ゼット)
|西山和広(Kazuhiro NISHIYAMA)

=end

Actions #25

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

At Sun, 21 Sep 2008 15:17:28 +0900,
Fujioka wrote:

  • 各々のエレメントの値は@encodingの値でforce_encodingし、
    valid_encoding?する。ただし、fileだけはASCII-8BITとする。

ファイルかどうかはどうやって判断するのでしょうか?

finenameがあったらASCII-8BIT固定にするのがいいかなと思っています。
ファイルも特別扱いしない方がいいと思いますか?

=end

Actions #26

Updated by naruse (Yui NARUSE) over 15 years ago

=begin
成瀬です。

Fujioka さんは書きました:

藤岡です。

At Sun, 21 Sep 2008 15:17:28 +0900,
Fujioka wrote:

  • 各々のエレメントの値は@encodingの値でforce_encodingし、
    valid_encoding?する。ただし、fileだけはASCII-8BITとする。
    ファイルかどうかはどうやって判断するのでしょうか?

finenameがあったらASCII-8BIT固定にするのがいいかなと思っています。
ファイルも特別扱いしない方がいいと思いますか?

Content-Type を見ればデータが文字列かバイナリかはわかるので、
それを見るのがいいのではないでしょうか。

=end

Actions #27

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

finenameがあったらASCII-8BIT固定にするのがいいかなと思っています。
ファイルも特別扱いしない方がいいと思いますか?

Content-Type を見ればデータが文字列かバイナリかはわかるので、
それを見るのがいいのではないでしょうか。

投稿してから私もそのほうがいいなと思っていました。
Content-Typeを見るように作ってみます。

=end

Actions #28

Updated by znz (Kazuhiro NISHIYAMA) over 15 years ago

=begin
西山和広です。

At Mon, 22 Sep 2008 01:11:44 +0900,
Fujioka wrote:

finenameがあったらASCII-8BIT固定にするのがいいかなと思っています。
ファイルも特別扱いしない方がいいと思いますか?

Content-Type を見ればデータが文字列かバイナリかはわかるので、
それを見るのがいいのではないでしょうか。

投稿してから私もそのほうがいいなと思っていました。
Content-Typeを見るように作ってみます。

受け取るCGI側ではなく送るUser-Agent側でASCII-8BITになるかどうか
決められると言うことは、encodingのチェックをすり抜けられるリクエストを
送りつけられると言うことになりそうですが、セキュリティ的に問題は
ないのでしょうか?

--
|ZnZ(ゼット エヌ ゼット)
|西山和広(Kazuhiro NISHIYAMA)

=end

Actions #29

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

finenameがあったらASCII-8BIT固定にするのがいいかなと思っています。
ファイルも特別扱いしない方がいいと思いますか?
Content-Type を見ればデータが文字列かバイナリかはわかるので、
それを見るのがいいのではないでしょうか。

投稿してから私もそのほうがいいなと思っていました。
Content-Typeを見るように作ってみます。

受け取るCGI側ではなく送るUser-Agent側でASCII-8BITになるかどうか
決められると言うことは、encodingのチェックをすり抜けられるリクエストを
送りつけられると言うことになりそうですが、セキュリティ的に問題は
ないのでしょうか?

エンコーディングのチェックはあくまで使い勝手の問題の話であって
セキュリティチェックのつもりはなかったので、問題ないと思っていました。
現状のcgi.rbではエンコーディングチェックは存在せず、
送りつけられたものはオブジェクトを生成します。
これをチェックするとしたら、
CGI.newでオプテョンを渡して受け取るエレメントとエンコーディングを
逐一指定する必要が出てきます。
そうなると使い勝手が悪いかなと思っています。

=end

Actions #30

Updated by Tietew (Toru Iwase) over 15 years ago

=begin

On Mon, 22 Sep 2008 01:11:44 +0900
In article
[[ruby-dev:36430] Re: [Feature #542] cgi.rb : CGI::unescape return encoding]
Fujioka wrote:

投稿してから私もそのほうがいいなと思っていました。
Content-Typeを見るように作ってみます。

通常のフィールドではContent-Typeは渡されませんが、ファイルの場合は
Content-Type:text/plain なんてこともあり得ます。
Content-Typeの有無は信頼性がないと思います。

--
Tietew
Blog: http://www.tietew.jp/
PGP: 26CB 71BB B595 09C4 0153 81C4 773C 963A D51B 8CAA

=end

Actions #31

Updated by Tietew (Toru Iwase) over 15 years ago

=begin

On Sun, 21 Sep 2008 15:17:28 +0900
In article
[[ruby-dev:36422] Re: [Feature #542] cgi.rb : CGI::unescape return encoding]
Fujioka wrote:

  • encodingのチェックをして正しくない場合はASCII-8BITに
    force_encodingしてしまう

例外を起こすか、何らかの形で「不正エンコーディングを検出した」ということ
を検出できる方法が欲しいです。

不正エンコーディングを検出したら 400 等のステータスで即終了。

--
Tietew
Blog: http://www.tietew.jp/
PGP: 26CB 71BB B595 09C4 0153 81C4 773C 963A D51B 8CAA

=end

Actions #32

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

投稿してから私もそのほうがいいなと思っていました。
Content-Typeを見るように作ってみます。

通常のフィールドではContent-Typeは渡されませんが、ファイルの場合は
Content-Type:text/plain なんてこともあり得ます。
Content-Typeの有無は信頼性がないと思います。

Content-Typeがあればファイルとみなすつもりでした。

  • encodingのチェックをして正しくない場合はASCII-8BITに
    force_encodingしてしまう

例外を起こすか、何らかの形で「不正エンコーディングを検出した」ということ
を検出できる方法が欲しいです。

不正エンコーディングを検出したら 400 等のステータスで即終了。

即終了するのはそのようにコーディングしてもらうとして、
何らかの形の部分の希望はありますか?
例えば@encoding_errorsのarrayを作って項目名をプッシュするとか

=end

Actions #33

Updated by Tietew (Toru Iwase) over 15 years ago

=begin

On Mon, 22 Sep 2008 11:22:44 +0900
In article
[[ruby-dev:36436] Re: [Feature #542] cgi.rb : CGI::unescape return encoding]
Fujioka wrote:

投稿してから私もそのほうがいいなと思っていました。
Content-Typeを見るように作ってみます。

通常のフィールドではContent-Typeは渡されませんが、ファイルの場合は
Content-Type:text/plain なんてこともあり得ます。
Content-Typeの有無は信頼性がないと思います。

Content-Typeがあればファイルとみなすつもりでした。

Content-Type の有無でファイルか否かは検出できなかったような。

  • encodingのチェックをして正しくない場合はASCII-8BITに
    force_encodingしてしまう

例外を起こすか、何らかの形で「不正エンコーディングを検出した」ということ
を検出できる方法が欲しいです。

不正エンコーディングを検出したら 400 等のステータスで即終了。

即終了するのはそのようにコーディングしてもらうとして、
何らかの形の部分の希望はありますか?
例えば@encoding_errorsのarrayを作って項目名をプッシュするとか

個人的には、どのフィールドが不正なのかということに興味はないので、
true/false が返る程度で構いません。他の人の意見も聞きたいです。

抜け穴を防ぐという意味では例外の方がいいのかなあ。

--
Tietew
Blog: http://www.tietew.jp/
PGP: 26CB 71BB B595 09C4 0153 81C4 773C 963A D51B 8CAA

=end

Actions #34

Updated by znz (Kazuhiro NISHIYAMA) over 15 years ago

=begin
西山和広です。

At Mon, 22 Sep 2008 18:55:07 +0900,
Tietew wrote:

  • encodingのチェックをして正しくない場合はASCII-8BITに
    force_encodingしてしまう

例外を起こすか、何らかの形で「不正エンコーディングを検出した」ということ
を検出できる方法が欲しいです。

不正エンコーディングを検出したら 400 等のステータスで即終了。

即終了するのはそのようにコーディングしてもらうとして、
何らかの形の部分の希望はありますか?
例えば@encoding_errorsのarrayを作って項目名をプッシュするとか

個人的には、どのフィールドが不正なのかということに興味はないので、
true/false が返る程度で構いません。他の人の意見も聞きたいです。

抜け穴を防ぐという意味では例外の方がいいのかなあ。

不正エンコーディングを検出したときに実行するブロックを指定できる
ようにして、指定がなかった場合のデフォルトは例外で、どのフィールドか
知りたければそこで残すようにするとか?

--
|ZnZ(ゼット エヌ ゼット)
|西山和広(Kazuhiro NISHIYAMA)

=end

Actions #35

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

CGI.new(:accept_encoding=>"...",
"name1"=>:file,
"name2"=>...)

で、検査しないなら

CGI.new(:accept_encoding=>:no_validation,
"name1"=>:file,
"name2"=>...)

とか。

こんな感じで項目毎にチェックを要求すると、
今あるウェブアプリ(tDiaryやHikiなども含む)は
軒並み設計をし直しになると思います。
理由はたいていのアプリはcgi=CGI.newをアプリの最初にやっておいて、
それからcgiを引き回す設計になっているからです。
また、CGI.newしたときにクエリをパースしているのですが、
CGI.newする前にURLはわかっていませんので、
どの項目を受け取れるようにするかを知らせることが困難です。
だからといって、ウェブアプリで使う項目を全部書くのも
現実的ではありませんし、動的な名前が受け付けられないのも困ります。
そのため、私は各項目名毎のチェックは入れたくありません。
セキュリティ的に問題だとしたら、容量チェックや
項目数の上限を設定する方が、
使い勝手の面でいいのではないかと思っています。

=end

Actions #36

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

  • encodingのチェックをして正しくない場合はASCII-8BITに
    force_encodingしてしまう
    例外を起こすか、何らかの形で「不正エンコーディングを検出した」ということ
    を検出できる方法が欲しいです。

不正エンコーディングを検出したら 400 等のステータスで即終了。

即終了するのはそのようにコーディングしてもらうとして、
何らかの形の部分の希望はありますか?
例えば@encoding_errorsのarrayを作って項目名をプッシュするとか
個人的には、どのフィールドが不正なのかということに興味はないので、
true/false が返る程度で構いません。他の人の意見も聞きたいです。

抜け穴を防ぐという意味では例外の方がいいのかなあ。

不正エンコーディングを検出したときに実行するブロックを指定できる
ようにして、指定がなかった場合のデフォルトは例外で、どのフィールドか
知りたければそこで残すようにするとか?

これ、コードのサンプルを作れませんでしょうか?
こんな風に使いたいみたいなやつ。

=end

Actions #37

Updated by znz (Kazuhiro NISHIYAMA) over 15 years ago

=begin
西山和広です。

At Mon, 22 Sep 2008 20:17:26 +0900,
Fujioka wrote:

不正エンコーディングを検出したときに実行するブロックを指定できる
ようにして、指定がなかった場合のデフォルトは例外で、どのフィールドか
知りたければそこで残すようにするとか?

これ、コードのサンプルを作れませんでしょうか?
こんな風に使いたいみたいなやつ。

Railsでvalidateにひっかかったときに赤い枠がついたりするような感じで
以下のように引っかかったフィールドに何か印をつけるのに使えるかも、
というイメージです。

invalid_fields = {}
cgi = CGI.new(..., :... =>proc {|field_name, field_value|
invalid_fields[field_name] = field_value
})
...
cgi.out(...) {
...
cgi.text_field({...,"name"=>"some_text", "class"=>
invalid_fields.include?("some_text") ? "invalid" : ""
})
...
}

--
|ZnZ(ゼット エヌ ゼット)
|西山和広(Kazuhiro NISHIYAMA)

=end

Actions #38

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

Railsでvalidateにひっかかったときに赤い枠がついたりするような感じで
以下のように引っかかったフィールドに何か印をつけるのに使えるかも、
というイメージです。

invalid_fields = {}
cgi = CGI.new(..., :... =>proc {|field_name, field_value|
invalid_fields[field_name] = field_value
})
...
cgi.out(...) {
...
cgi.text_field({...,"name"=>"some_text", "class"=>
invalid_fields.include?("some_text") ? "invalid" : ""
})
...
}

こんな感じでしょうか。
invalid_fields={}
cgi=CGI.new(:accept_charset=>"EUC-JP"){|field_name,field_value|
invalid_fields[field_name] = field_value
}
こんな感じで使えます。newのブロックに渡すのはいいのかどうか微妙ですが。
メソッドのブロックが空いているので詰め込んでみました。

Index: lib/cgi/core.rb

--- lib/cgi/core.rb (リビジョン 19454)
+++ lib/cgi/core.rb (作業コピー)
@@ -598,8 +598,21 @@

stdinput.read(Integer(env_table['CONTENT_LENGTH'])) or ''
else
read_from_cmdline

  •                end
    
  •                end.dup.force_encoding(@accept_charset)
                 )
    
  •    if @accept_charset!="ASCII-8BIT" ||
    

@accept_charset!=Encoding::ASCII_8BIT

  •      @params.each do |key,values|
    
  •        values.each do |value|
    
  •          unless value.valid_encoding?
    
  •            if @accept_charset_error_block
    
  •              @accept_charset_error_block.call(key,value)
    
  •            else
    
  •              raise "Accept-Charset encoding error"
    
  •            end
    
  •          end
    
  •        end
    
  •      end
    
  •    end
     end
    
     @cookies = CGI::Cookie::parse((env_table['HTTP_COOKIE'] or
    

env_table['COOKIE']))
@@ -665,7 +678,24 @@
# from the command line or (failing that) from standard input.
Otherwise,
# cookies and other parameters are parsed automatically from the standard
# CGI locations, which varies according to the REQUEST_METHOD.

  • def initialize(type = "query")
  • attr_reader :accept_charset
  • @@accept_charset="UTF-8"
  • def self.accept_charset
  • @@accept_charset
  • end
  • def self.accept_charset=(accept_charset)
  • @@accept_charset=accept_charset
  • end
  • def initialize(options = {},&block)
  • @accept_charset_error_block=block if block_given?
  • @options={:accept_charset=>@@accept_charset}
  • case options
  • when Hash
  •  @options.merge!(options)
    
  • when String
  •  @options[:tag_maker]=options
    
  • end
  • @accept_charset=@options[:accept_charset]
    if defined?(MOD_RUBY) && !ENV.key?("GATEWAY_INTERFACE")
    Apache.request.setup_cgi_env
    end
    @@ -677,7 +707,7 @@
    @output_cookies = nil
    @output_hidden = nil
  • case type
  • case @options[:tag_maker]
    when "html3"
    require 'cgi/html'
    extend Html3

=end

Actions #39

Updated by xibbar (Takeyuki FUJIOKA) over 15 years ago

=begin
藤岡です。

こんな感じでしょうか。
invalid_fields={}
cgi=CGI.new(:accept_charset=>"EUC-JP"){|field_name,field_value|
invalid_fields[field_name] = field_value
}
こんな感じで使えます。newのブロックに渡すのはいいのかどうか微妙ですが。
メソッドのブロックが空いているので詰め込んでみました。

大きな反対がなければ明日あたりにとりあえずコミットしてしまう予定です。
マルチパートのほうはまだ何もやっていませんが、
エンコーディング以前に動きそうにないので、
今後対応していきます。

=end

Actions

Also available in: Atom PDF

Like0
Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0