Bug #5390

YAML.load が、正しく解析できないエンコーディングの文字列も受け付けてしまう

Added by yu nobuoka over 3 years ago. Updated almost 3 years ago.

[ruby-dev:44573]
Status:Closed
Priority:Normal
Assignee:Aaron Patterson
ruby -v:ruby 1.9.2p290 (2011-07-09 revision 32553) [x86_64-linux] Backport:

Description

[] にてバグ扱いでいいだろうという話がありましたのでバグとして報告します。

YAML.load がどのように実装されているのかコードを追いきれなかったのですが、動きを見る限り、与えられた文字列のエンコーディングを気にせずにパースしているように思います。 このため、Shift_JIS のようなエンコーディングの文字列の一部を正しくパースできません。

--- source code ---
# coding: Shift_JIS
require "yaml"
text = '[ "噂" ]' # Shift_JIS の '噂' の 2 バイト目はバックスラッシュと同じバイト値
str = YAML.load( text ).first # エラー発生

--- output ---
/home/nobuoka/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/syck.rb:135:in load': syntax error on line 0, col 9:' (ArgumentError)
from /home/nobuoka/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/syck.rb:135:in load'
from yaml_cp932.rb:4:in
'

Shift_JIS の文字列でもほとんどの場合は例外発生せずにパースされるので、Shift_JIS の文字列を使っている場合に問題が起こる可能性をユーザーが認識しづらいという問題があります。 よって、現在の動きはバグとして、以下のいずれかの動きに変更した方が良いのではないでしょうか。

*UTF-8 (UTF-16 も?) 以外のエンコーディングの文字列が渡された場合に例外を発生させる
*UTF-8 以外のエンコーディングの文字列が渡された場合に、自動的に UTF-8 に変換して処理を進める
*YAML の解析部分でエンコーディングを考慮するようにして、Shift_JIS などでも正しく解析できるようにする

History

#1 Updated by Yui NARUSE over 3 years ago

  • Status changed from Open to Assigned
  • Assignee set to Aaron Patterson

*UTF-8 以外のエンコーディングの文字列が渡された場合に、自動的に UTF-8 に変換して処理を進める
がいいのではないかと思っています。

*YAML の解析部分でエンコーディングを考慮するようにして、Shift_JIS などでも正しく解析できるようにする
なお、これはYAMLの仕様にエンコーディングを与える方法が規定されていないので、YAML仕様の範囲内では不可能なはずです。

#2 Updated by Ayumu AIZAWA about 3 years ago

YAML::ENGINE.yamler が syck のみ再現します。
ruby1.9.2 をお使いの場合は require 'yaml' する前に require 'psych' するか YAML::ENGINE.yamler = 'psych' すると以下のようにPsych::SyntaxErrorとなります。

---- ruby 2.0.0dev
$ cat bug_5390.rb
# coding: Shift_JIS
require 'yaml'
text = '["?\"]'
p YAML::ENGINE.yamler
p text.encoding
str = YAML.load(text).first

$ ruby -v bug_5390.rb
ruby 2.0.0dev (2011-12-30 trunk 34161) [x86_64-darwin10.8.0]
"psych"
#Encoding:Shift_JIS
/Users/ayumin/tmp/ruby/lib/ruby/2.0.0/psych.rb:192:in parse': (<unknown>): invalid leading UTF-8 octet at line 1 column 1 (Psych::SyntaxError)
from /Users/ayumin/tmp/ruby/lib/ruby/2.0.0/psych.rb:192:in
parse_stream'
from /Users/ayumin/tmp/ruby/lib/ruby/2.0.0/psych.rb:150:in parse'
from /Users/ayumin/tmp/ruby/lib/ruby/2.0.0/psych.rb:126:in
load'
from bug_5390.rb:6:in `'

---- ruby1.9.2

$ cat bug_5390.rb
# coding: Shift_JIS
require 'yaml'
text = '["?\"]'
YAML::ENGINE.yamler = 'psych'
str = YAML.load(text).first

$ ruby -v bug_5390.rb
ruby 1.9.2p290 (2011-07-09 revision 32553) [x86_64-darwin10.8.0]
/Users/ayumin/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/psych/deprecated.rb:79: warning: method redefined; discarding old to_yaml_properties
/Users/ayumin/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/syck/rubytypes.rb:13: warning: previous definition of to_yaml_properties was here
/Users/ayumin/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/psych.rb:148:in parse': couldn't parse YAML at line 1 column 0 (Psych::SyntaxError)
from /Users/ayumin/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/psych.rb:148:in
parse_stream'
from /Users/ayumin/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/psych.rb:119:in parse'
from /Users/ayumin/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/psych.rb:106:in
load'
from bug_5390.rb:5:in `'

#3 Updated by Aaron Patterson about 3 years ago

返事が遅くなって、ごめんなさい。

YAML のファイルフォーマットは UTF8, UTF16LE, と UTF16BE のみサポートしますが、Psych だけは String をパースする時に文字コードを UTF8 に変換します。

例: https://gist.github.com/1902995

ファイルを使用する場合、ファイルの文字例は以下の UTF8 、UTF16LE 、 UTF16BEの一つのみ使用可能です。

例:https://gist.github.com/1903026

#4 Updated by Ayumu AIZAWA almost 3 years ago

  • Status changed from Assigned to Closed

1.9.2はもうすぐメンテナンス終了で、1.9.3からPsychがデフォルトです。
こちらのチケットはCloseします。

Also available in: Atom PDF